[Haskell-beginners] Wrong type inferred for polymorphic function in a case alternative

Ramin Honary ramin.honary at gmail.com
Wed Apr 11 17:06:28 CEST 2012

Hi everyone,

I am using GHC 7.0.4.
I boiled-down my problem into a simple program which I attached to
this message. I don't know how to get the program to compile.

I need to pass arbitrary class member functions as a parameter to a
very large, complex, polymorphic function called "apply", and have
this class member function applied to abitrary fields of data
constructors of a very large, complex data type.

What I expect to happen is this:
For each case alternative, GHC will infer the type of the polymorphic
function from the matched pattern in the case alternative, and use
that inference to select the correct instance function for that type.
So for case alternative (TA x, TA y) -> TA (fn x y), the correct
instance for "fn" is selected based on the type of "x" and "y" which
are determined by the pattern match, and by the type of "TA". If that
case alternative does not match, then it should try the next
alternative (TB x, TB y) -> TB (fn x y), and since "fn" is
polymorphic, it will still be able to select the correct instance for
the type given by the pattern match. So I can pass "f1" or "f2" or
"f3" to "apply" as the "fn" parameter, and have the correct instance
of "f1" or "f2" or "f3" be selected depending on where in the "case"
expression "fn" is used.

What is actually happening is:
GHC arbitrarily selects one of the case alternatives (usually the last
case alternative, sometimes the first) and decides that from now on
this one type is the type for "fn" for every case alternative. So for
every other case alternative, it decides that "fn" is of the wrong
type and rejects the program, rather than trying to infer a different
type for "fn" specific to this case alternative. Said another way, the
type inference algorithm is being too strict, and I would like it to
be more lazy, computing the type once per each case alternative,
rather than computing the type only once for the entire case
statement. Is there a language option for that?

I have tried using language options, like -XNoMonoPatBinds
-XNoMonomorphismRestriction -XMonoLocalBinds -XPolymorphicComponents
-XImpredicativeTypes, but none of those help. My current solution is
to use Template Haskell and make the "apply" function a splice, so the
whole case statement is copied to every place it is used (which takes
a very, very long for it time to comple). Is there a way to do this
without Template Haskell? Can I get GHC to behave as I expected it to?

-------------- next part --------------
A non-text attachment was scrubbed...
Name: ABC.hs
Type: application/octet-stream
Size: 2067 bytes
Desc: not available
URL: <http://www.haskell.org/pipermail/beginners/attachments/20120412/2f74c3f9/attachment.obj>

More information about the Beginners mailing list