NoMonomorphismRestriction forces odd situation when using contexts

Hello, Consider the following program: ------------------------------------------------------------------- -- bar.hs {-# LANGUAGE NoMonomorphismRestriction #-} data Status = Foo | Bar data Rec m a = Rec { get :: m a , status :: Status } defRec :: (Monad m) => Rec m a defRec = undefined myRec :: (Monad m) => Rec m a myRec = Rec x y where Rec x y = defRec ------------------------------------------------------------------- It doesn't compile (under GHC 7.10.2), the error is: bar.hs:16:7: No instance for (Monad t0) The type variable ‘t0’ is ambiguous When checking that ‘y’ has the inferred type y :: Status Probable cause: the inferred type is ambiguous In an equation for ‘myRec’: myRec = Rec x y where Rec x y = defRec Failed, modules loaded: none. If you remove the language extension, it does. Keeping the NoMonomorphismRestriction, it can be forced to typecheck by putting in a "dummy" type that satifies the constraint when obtaining the field `status` (that doesn't depend on `m`. ------------------------------------------------------------------- -- bar.hs {-# LANGUAGE NoMonomorphismRestriction #-} data Status = Foo | Bar data Rec m a = Rec { get :: m a , status :: Status } defRec :: (Monad m) => Rec m a defRec = undefined myRec :: (Monad m) => Rec m a myRec = Rec x y where s :: Rec Maybe a -> Status s = status x = get defRec -- y = s defRec ------------------------------------------------------------------- So, what's going on here? Is this a feature of this extension? It seems like the ability to destructure and then recombine is pretty fundamental, and it shouldn't break in the way that it does. (I.e. it's kinda crazy to have to put in a dummy type satisfying the constraint; is there some way to pass down the error -- Noon Silk, ن https://silky.github.io/ "Every morning when I wake up, I experience an exquisite joy — the joy of being this signature."

On 2015-12-20 08:01 PM, Noon Silk wrote:
{-# LANGUAGE NoMonomorphismRestriction #-}
data Status = Foo | Bar
data Rec m a = Rec { get :: m a , status :: Status }
defRec :: (Monad m) => Rec m a defRec = undefined
myRec :: (Monad m) => Rec m a myRec = Rec x y where Rec x y = defRec
Why this is an ambiguous-type error is a really long story. But a factor is analogous to "show . read". Another factor is that since you turn off the monomorphism restriction, there is a type generalization step, and the generalizing of y's type is separate from the generalization of x's type. I have found this solution, it works by connecting types to suppress the generalize step: {-# LANGUAGE NoMonomorphismRestriction, ScopedTypeVariables #-} ... myRec :: forall m a. (Monad m) => Rec m a myRec = Rec x y where Rec x y = defRec :: Rec m a

Hi Albert,
Thanks for your response (and sorry about my earlier email missing some
content at the end; I rushed out to lunch as I was sending this).
Your solution works fine. It's better than the option I've listed.
On Wed, Dec 23, 2015 at 7:57 AM, Albert Y. C. Lai
On 2015-12-20 08:01 PM, Noon Silk wrote:
{-# LANGUAGE NoMonomorphismRestriction #-}
data Status = Foo | Bar
data Rec m a = Rec { get :: m a , status :: Status }
defRec :: (Monad m) => Rec m a defRec = undefined
myRec :: (Monad m) => Rec m a myRec = Rec x y where Rec x y = defRec
Why this is an ambiguous-type error is a really long story. But a factor is analogous to "show . read". Another factor is that since you turn off the monomorphism restriction, there is a type generalization step, and the generalizing of y's type is separate from the generalization of x's type.
I have found this solution, it works by connecting types to suppress the generalize step:
{-# LANGUAGE NoMonomorphismRestriction, ScopedTypeVariables #-} ... myRec :: forall m a. (Monad m) => Rec m a myRec = Rec x y where Rec x y = defRec :: Rec m a
_______________________________________________ Haskell-Cafe mailing list Haskell-Cafe@haskell.org http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe
-- Noon Silk, ن https://sites.google.com/site/noonsilk/ "Every morning when I wake up, I experience an exquisite joy — the joy of being this signature."

You can avoid this problem by using a case-expression, which remains monomorphic: myRec = case defRec of Rec x y -> Rec x y
participants (3)
-
Albert Y. C. Lai
-
Noon Silk
-
Phil Ruffwind