[Haskell-cafe] Re: Why I Love Haskell In One Simple Example

Bernard Pope bjpop at cs.mu.OZ.AU
Mon Jun 27 20:07:06 EDT 2005

On Mon, 2005-06-27 at 22:12 +0200, Mads Lindstrøm wrote:

> > > I had newer seen anybody use "forall a." in function signatures before,
> > > and therefore was curious about its effect. This is probably do to my
> > > inexperience regarding Haskell. 

The "forall a." syntax is not Haskell 98. The universal quantification
of type variables is implicit in type signatures for polymorphic
functions, so there is no need to write it.

Haskell extensions have gone beyond the polymorphism allowed in Haskell
98, and thus have needed to disambiguate different types with explicit
quantifiers. Hence, glasgow-exts and hugs -98 allow an explicit forall.

> > If you omit it, the compiler will decide that test is some arbitrary
> > type (Double, Integer, whatever).  

I think John is talking about the monomorphism restriction and
defaulting. The use of the forall syntax is orthogonal to this.

> > Note that test in this example is not a function.
> OK, I assumed it was, as I thought all functions started with lower case
> and all modules, classes, and data/type constructors started with upper
> case. It does not take any variables as input, but that is still a
> function in my book (but I could be wrong there. I am no mathematician).

This kind of declaration:

   f = rhs

is called a "pattern binding" in Haskell. In contrast to this kind of

   g pat1 pat2 ... patn = rhs

which is called a function binding.

g is always a function, but f might be bound to a constant expression,
or it might be bound to a function. Now, for convenience, people might
say f and g are functions, even when f is bound to a constant

Here's where it gets tricky: pattern bindings can be overloaded (so can
function bindings, but they are less tricky). When a pattern binding is
overloaded it is as if it has an implicit argument, which corresponds to
a type class dictionary (a structure that contains concrete
implementations of the classes overloaded functions). In that situation
you can imagine that the bound variable is a function whose (only)
argument is the dictionary - only you don't pass it in explicitly, the
compiler adds it for you. 

This brings us to the monomorphism restriction, which John was talking
about. This rule says that a pattern binding is not allowed to be
overloaded unless you supply an explicit type signature that says it is
overloaded. I won't go into the justification for this (it is a
contentious point, read the Haskell Report if you like).


More information about the Haskell-Cafe mailing list