
... I never understood why (->) is right associative in types, but (=>) is not and you are instead supposed to pack constraints in a tuple.
`-XRankNTypes` enables something called Rank 1 types, which accepts this:
foo :: Ord a => Num b => a -> Show b => b
-- foo :: (Ord a, Num b, Show b) => a -> b -- inferred/canonical
We should also have:
bar :: forall a. forall {- empty -}. forall b. blah
-- bar :: forall a b. blah -- equivalent
But `PatternSynonyms` drives a cart and horses through that: you must have exactly 2 `... => ... => ...` and exactly 2 `forall`s (possibly empty) -- that is, if you explicitly quantify at all. Or you can go:
MyPat :: Num a => a -> Baz a -- which is shorthand for
MyPat :: Num a => () => a -> Baz a -- which is equiv to
MyPat :: Num a => Num a => a -> Baz a
MyPat :: () => Num a => a -> Baz a -- this means something different