Now of course, the followup question is "what the heck is a
monomorphism restriction and why would I want it?"
Here is a simple example:
expensiveComputation :: Num a => a -> a
expensiveComputation x = ... something that takes a long time to compute ...
ghci> :t (expensiveComputation 2 *)
(expensiveComputation 2 *) :: Num a => a -> a
Now consider these two functions
g = let c = expensiveComputation 2 in (c*)
f x = let c = expensiveComputation 2 in (c*x)
g is a simple pattern binding, so without looking at the RHS, one
expects it to be calculated once and the result shared, in a way like
this:
c = expensiveComputation 2 -- lazily evaluated, only once
g = (c*)
But if you give g the more general type signature, the
expensiveComputation has to get run *every time g is called*. This is
because there's no way to create a single storage cell for c; there's
a possible answer for every single type that is an instance of Num.
f makes it clear; c does not get evaluated until the arguments are
saturated and is locally allocated. So it's alright to give it the
polymorphic type.
-- ryan
On Wed, Nov 17, 2010 at 10:31 AM, Daniel Fischer
<daniel.is.fischer at web.de> wrote:
> On Wednesday 17 November 2010 19:09:16, Jerzy M wrote:
>> Hallo,
>> let me take this simple function: (2*).
>> If I check its type
>>>> :t (2*)
>>>> I'll obtain
>> (2*) :: (Num a) => a -> a
>>>> But now it suffices to write
>> g = (2*)
>> and check
>>>> :t g
>>>> to obtain
>> g :: Integer -> Integer
>>>> One more combination, now I write
>> h x = (2*) x
>> and check once more
>>>> :t h
>>>> to get
>> h :: (Num a) => a -> a
>>>> So my question is: why (in this second example) Integer is inferred?
>> What makes a difference?
>> The monomorphism restriction.
> As specified in section 4.5.5 of the language report
> (http://www.haskell.org/onlinereport/haskell2010/haskellch4.html#x10-930004.5.5),
> values bound by a (simple) pattern binding (basically, not bound by a
> binding with function arguments to the left of '=') which don't have
> explicit type signatures get a monomorphic type (ambiguous type variables
> are resolved per the defaulting rules of section 4.3 if possible).
>> So
>> g = (2*)
>> is a simple pattern binding without type signature, hence it gets a
> monomorphic type.
> The inferred type is
>> g :: Num a => a -> a
>> and by the defaulting rules (unless you have an explicit default
> declaration in the module where g is defined), the ambiguous type variable
> a is resolved to Integer.
>> h x = (2*) x
>> is a function binding, hence h gets the inferred polymorphic type.
>> The MR is often inconvenient (it may be removed in future language
> standards, I'm not up to date with the standings of that proposal), so it
> can be disabled (at least in GHC).
> In normal code, it's not so frequent a matter (on one hand, there's more
> context in the module than at the ghci prompt, on the other hand, modules
> contain more type signatures), so it's comparatively rare to need
> {-# LANGUAGE NoMonomorphismRestriction #-}.
> At the ghci prompt, however, it's a frequent cause of surprise, so it may
> be a good idea to put the line
>> :set -XNoMonomorphismRestriction
>> in your ~/.ghci file.
>> Cheers,
> Daniel
> _______________________________________________
> Haskell-Cafe mailing list
>Haskell-Cafe at haskell.org>http://www.haskell.org/mailman/listinfo/haskell-cafe>