
I haven't thought about how to implement such a thing. At the least, it would probably require some annotation saying that we expect `\HNil -> ()` to be exhaustive (as GHC won't, in general, make that assumption). Even with that, could we get type inference to behave? Possibly.
As I wrote in another post on this thread, it’s a bit tricky.
What would you expect of (EX1)
\x -> case x of HNil -> blah
Here the lambda and the case are separated
Now (EX2)
\x -> (x, case x of HNil -> blah)
Here the lambda and the case are separated more, and x is used twice.
What if there are more data constructors that share a common return type? (EX3)
data HL2 a where
HNil1 :: HL2 []
HNil2 :: HL2 []
HCons :: …blah…
\x -> case x of { HNil1 -> blah; HNil 2 -> blah }
Here HNil1 and HNil2 both return HL2 []. Is that “singular”?
What if one was a bit more general than the other? Do we seek the least common generalisation of the alternatives given? (EX4)
data HL3 a where
HNil1 :: HL2 [Int]
HNil2 :: HL2 [a]
HCons :: …blah…
\x -> case x of { HNil1 -> blah; HNil 2 -> blah }
What if the cases were incompatible? (EX5)
data HL4 a where
HNil1 :: HL2 [Int]
HNil2 :: HL2 [Bool]
HCons :: …blah…
\x -> case x of { HNil1 -> blah; HNil 2 -> blah }
Would you expect that to somehow generalise to `HL4 [a] -> blah`?
What if x matched multiple times, perhaps on different constructors (EX6)
\x -> (case s of HNil1 -> blah1; case x of HNil2 -> blah)
The water gets deep quickly here. I don’t (yet) see an obviously-satisfying design point that isn’t massively ad-hoc.
Simon
From: ghc-devs