11
votes

If we have an expression:

a $ b @ c

$ is a left-associative operator, @ is right-associative. They have the same precedence.

How is this expression parsed? As (a $ b) @ c or as a $ (b @ c)?

2
An actual C or C++ example would probably be more clear. - chris
In what language? Your own? Well, don't do that then! It's an ambiguous grammar which doesn't have a single way to resolve. - Pubby
It is determined by the compiler how to analysis the grammar tree.Reading <<Compilers principles, techniques, and tools>> will help you a lot. - MYMNeo

2 Answers

12
votes

This is an excellent question. While Dipstick is correct that in many languages, operator precedences and associativities are defined to avoid such a problem, there are languages in which such a situation may arise.

Haskell is such a language. It allows you to define your own infix operators, and their precedences (integer from 0 to 9) and associativity (left, right, non). It's easy to create the preconditions for the scenario you described:

infixl 5 $$
($$) :: Int -> Int -> Int
a $$ b = a + b

infixr 5 @@
(@@) :: Int -> Int -> Int
a @@ b = a * b

And then the situation itself:

uhoh = 1 $$ 2 @@ 3

This results in this error message:

Precedence parsing error
    cannot mix `$$' [infixl 5] and `@@' [infixr 5] in the same infix expression

Of course, Haskell's solution -- aborting with a parse error -- is not the only way to deal with this problem, but it is certainly a reasonable one.

For more information about operator parsing in Haskell, please see section 4.4.2 of the Haskell report.

6
votes

Operators at the same precedence are all either right associative or all left associative so the problem doesn't arise.