There are two things going on. 1. Hugs deals with mutual recursion in a more sophisticated way than GHC. Mark T is absolutely right, and the THIH paper explains.
2. Furthermore,GHC implements the H98 requirement that the context of all functions in a mutually recursive groups must be the same. So f :: Eq a => ... g :: Ord a => ... is illegal if f and g are mutually recursive. Both these things arise from the way GHC translates mutually recursive overloaded defns. Consider f :: Ord a => a -> a -> a f x y = ...(x==y)...(x>y)...(f y x)... GHC translates it thus: f ord_dict = let gr = select_gr ord_dict eq_dict = select_eq ord_dict eq = select_eq eq_dict fm x y = ...(eq x y)...(ord x y) ...(fm y x)... in fm Note that all the dictionary selection (and sometimes construction) is done outside the loop, implemented by 'fm'. Matters get more complicated when there is mutual recursion; suffice it it say that in order to pull the dictionary manipuation outside the loop, all the contexts must be the same. Arguably, H98 and GHC are wrong, and the restrictions should be lifted. GHC usually errs on the side of lifting restrictions (with -fglasgow-exts) but on this occasion the benefit seemed slight, while it turns out that the cost of changing the way let/where is dealt with is not inconsiderable. So I've let sleeping dogs lie. I think it's a corner case that seldom matters. Counter examples to this claim would be interesting. At least I hope this explains what's happening. Simon | -----Original Message----- | From: Mark Tullsen [mailto:[EMAIL PROTECTED]] | Sent: 09 August 2002 20:31 | To: [EMAIL PROTECTED] | Cc: Arthur Baars | Subject: Re: GHC bug,or Hugs feature? | | | I believe the incompatibilities are explained thus: | | In section 4.5.1 of the Haskell Report it only states that | "A dependency analysis transformation is first performed | to increase | polymorphism" | | But hugs appears to be using a more refined version of the | dependency | analysis as explained in section 11.6.3 of Mark Jones' paper Typing | Haskell in Haskell. Read that section. | | - Mark | | | Arthur Baars wrote: | > In Mark Jones' paper Typing Haskell in Haskell, I found the | following | > example(in the section on binding-groups): | > | > f :: Eq a => a -> Bool | > f x = x==x || g True | > g y = y<=y || f True | > | > According to the paper the inferred type of g should be: | g::Ord a => | > a -> Bool | > | > Hugs infers this type but GHC infers the following | *ambiguous* type: | > *Main> :i g | > -- g is a variable, defined at Test.hs:25 | > g :: forall a. (Eq a) => Bool -> Bool | > | > When adding an explicit type signature for g, Hugs happily | accepts the | > code, but GHC gives the following error: | > | > f :: Eq a => a -> Bool | > f x = x==x || g True | > g :: Ord a => a -> Bool | > g y = y<=y || f True | > | > Test.hs:24: | > Couldn't match `{Ord a}' against `{Eq a1}' | > When matching the contexts of the signatures for | > g :: forall a. (Ord a) => a -> Bool | > f :: forall a. (Eq a) => a -> Bool | > The signature contexts in a mutually recursive group | should all be | > identical | > When generalising the type(s) for g, f | > Failed, modules loaded: none. | > | > I think the problems are caused by differences in the binding group | > analysis in Hugs and GHC. | > | > Malcolm, could you check what NHC says about the examples above? | > | > Cheers, | > Arthur | > | > _______________________________________________ | > Haskell mailing list | > [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell | > | | | _______________________________________________ | Haskell mailing list | [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell | _______________________________________________ Haskell mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell