Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does Haskell precedence have only 10 levels? Is the figure of 10 enough?

I want to know why Haskell designers agreed to allow only 10 levels of precedence? Has anybody found it insufficient ?

like image 759
Niket Kumar Avatar asked Jun 12 '11 05:06

Niket Kumar


1 Answers

To the best of my knowledge, it's completely arbitrary. All the documentation I'm aware of simply states it as a point of fact, with no elaboration or justification.

But if you think about it, why would anything else be better? Okay, let's say 10 isn't enough. You've got (.) which has the highest fixity and you want something else that binds a bit tighter. You add an extra level, so your new maximum is 10 (even though most fixities only go to 9).

Now you have 11 levels of precedence. (That's ridiculous. It's not even funny.) How is this any less arbitrary than 10? What's to stop you from adding more? What if you want new levels between existing ones? Sure, you can keep adding more, until eventually you find yourself writing infix↑ (ω + 2i) and wondering where your life went wrong.

The thing is, operator precedence is inherently a pretty arbitrary thing. There are a few conventions--multiplicative things binding tighter than additive ones, logical operators having lower precedence than boolean-valued functions like (==)--but those are somewhat limited, and usually don't cover more than a few levels. Otherwise, the only way to remember operator precedences is to... well, remember them, as in simply memorize each one. Not only is this a chore, it can make code opaque to others who may not have everything memorized as well. Human working memory is a very limited resource, so the fewer picky details that need to be recalled while coding, the better.

Most uses of operators in Haskell where precedence matters fall into one of several rough groups:

  • Pseudosyntactic operators like the common use of ($), which typically need extremely high or low precedence to avoid conflicting with other operators.

  • Expressions using standard operators, or variations thereof, where a handful of standard precedence levels exist and new operators should generally share the same level as whatever they're based on.

  • Specialized operator sets, such as for an EDSL, whose symbols and precedence levels are typically chosen to reflect the nature of the EDSL and are unlikely to coexist with other sets of operators.

All of those manage just fine with only a few precedence levels. More importantly, they're characterized by either being effectively independent of other operators or only used together with a very limited set of other operators. Start adding in more operators and mixing them together in single expressions and pretty soon people will start using explicit parentheses anyway because they can't remember what binds more tightly than what. Speaking for myself, I'm already prone to explicit parenthesization when mixing EDSL-style operators (say, Arrow combinators) with logical operators because I can't usually recall the exact precedence levels each one has.

So, having established that: 1) lots of extra precedence levels wouldn't be that useful because it's too much to keep track of, and 2) any limit we pick is going to be equally arbitrary... why 10? I'm going to guess "because then fixity values are only single digits".

like image 191
C. A. McCann Avatar answered Sep 27 '22 20:09

C. A. McCann