<option>-XPostfixOperators</option>,
<option>-XPatternGuards</option>,
<option>-XLiberalTypeSynonyms</option>,
+ <option>-XExplicitForAll</option>,
<option>-XRankNTypes</option>,
<option>-XImpredicativeTypes</option>,
<option>-XTypeOperators</option>,
- <option>-XRecursiveDo</option>,
+ <option>-XDoRec</option>,
<option>-XParallelListComp</option>,
<option>-XEmptyDataDecls</option>,
<option>-XKindSignatures</option>,
<title>The recursive do-notation
</title>
-<para> The recursive do-notation (also known as mdo-notation) is implemented as described in
-<ulink url="http://citeseer.ist.psu.edu/erk02recursive.html">A recursive do for Haskell</ulink>,
-by Levent Erkok, John Launchbury,
-Haskell Workshop 2002, pages: 29-37. Pittsburgh, Pennsylvania.
-This paper is essential reading for anyone making non-trivial use of mdo-notation,
-and we do not repeat it here.
-</para>
<para>
-The do-notation of Haskell does not allow <emphasis>recursive bindings</emphasis>,
+The do-notation of Haskell 98 does not allow <emphasis>recursive bindings</emphasis>,
that is, the variables bound in a do-expression are visible only in the textually following
code block. Compare this to a let-expression, where bound variables are visible in the entire binding
group. It turns out that several applications can benefit from recursive bindings in
-the do-notation, and this extension provides the necessary syntactic support.
+the do-notation. The <option>-XDoRec</option> flag provides the necessary syntactic support.
</para>
<para>
-Here is a simple (yet contrived) example:
-</para>
+Here is a simple (albeit contrived) example:
<programlisting>
+{-# LANGUAGE DoRec #-}
import Control.Monad.Fix
-justOnes = mdo xs <- Just (1:xs)
- return xs
+justOnes = do { rec { xs <- Just (1:xs) }
+ ; return (map negate xs) }
</programlisting>
+The <literal>rec</literal>
+As you can guess <literal>justOnes</literal> will evaluate to <literal>Just [-1,-1,-1,...</literal>.
+</para>
<para>
-As you can guess <literal>justOnes</literal> will evaluate to <literal>Just [1,1,1,...</literal>.
+The background and motivation for recusrive do-notation is described in
+<ulink url="http://citeseer.ist.psu.edu/erk02recursive.html">A recursive do for Haskell</ulink>,
+by Levent Erkok, John Launchbury,
+Haskell Workshop 2002, pages: 29-37. Pittsburgh, Pennsylvania.
+This paper is essential reading for anyone making non-trivial use of mdo-notation,
+and we do not repeat it here. However, note that GHC uses a different syntax than the one
+in the paper.
</para>
+<sect3>
+<title>Details of recursive do-notation</title>
+<para>
+The recursive do-notation is enabled with the flag <option>-XDoRec</option> or, equivalently,
+the LANGUAGE pragma <option>DoRec</option>. It introduces the single new keyword "<literal>rec</literal>",
+which wraps a mutually-recusrive group of monadic statements,
+producing a single statement. Similar to a <literal>let</literal>
+statement, the variables bound in the <literal>rec</literal> are
+visible throughout the <literal>rec</literal> group, and below it.
+</para>
<para>
The Control.Monad.Fix library introduces the <literal>MonadFix</literal> class. Its definition is:
</para>
dictates how the required recursion operation should be performed. For example,
<literal>justOnes</literal> desugars as follows:
<programlisting>
-justOnes = mfix (\xs' -> do { xs <- Just (1:xs'); return xs }
+justOnes = do { xs <- mfix (\xs' -> do { xs <- Just (1:xs'); return xs })
+ ; return (map negate xs) }
</programlisting>
-For full details of the way in which mdo is typechecked and desugared, see
-the paper <ulink url="http://citeseer.ist.psu.edu/erk02recursive.html">A recursive do for Haskell</ulink>.
-In particular, GHC implements the segmentation technique described in Section 3.2 of the paper.
-</para>
-<para>
-If recursive bindings are required for a monad,
-then that monad must be declared an instance of the <literal>MonadFix</literal> class.
-The following instances of <literal>MonadFix</literal> are automatically provided: List, Maybe, IO.
-Furthermore, the Control.Monad.ST and Control.Monad.ST.Lazy modules provide the instances of the MonadFix class
-for Haskell's internal state monad (strict and lazy, respectively).
+In general, a <literal>rec</literal> statment <literal>rec <replaceable>ss</replaceable></literal>
+is desugared to the statement
+<programlisting>
+ <replaceable>vs</replaceable> <- mfix (\~<replaceable>vs</replaceable> -> do { <replaceable>ss</replaceable>
+ ; return <replaceable>vs</replaceable> })
+</programlisting>
+where <replaceable>vs</replaceable> is a tuple of the varaibles bound by <replaceable>ss</replaceable>.
+Moreover, the original <literal>rec</literal> typechecks exactly
+when the above desugared version would do so. (For example, this means that
+the variables <replaceable>vs</replaceable> are all monomorphic in the statements
+following the <literal>rec</literal>, because they are bound by a lambda.)
</para>
<para>
-Here are some important points in using the recursive-do notation:
+Here are some other important points in using the recursive-do notation:
<itemizedlist>
<listitem><para>
-The recursive version of the do-notation uses the keyword <literal>mdo</literal> (rather
-than <literal>do</literal>).
+It is enabled with the flag <literal>-XDoRec</literal>, which is in turn implied by
+<literal>-fglasgow-exts</literal>.
</para></listitem>
<listitem><para>
-It is enabled with the flag <literal>-XRecursiveDo</literal>, which is in turn implied by
-<literal>-fglasgow-exts</literal>.
+If recursive bindings are required for a monad,
+then that monad must be declared an instance of the <literal>MonadFix</literal> class.
+The following instances of <literal>MonadFix</literal> are automatically provided: List, Maybe, IO.
+Furthermore, the Control.Monad.ST and Control.Monad.ST.Lazy modules provide the instances of the MonadFix class
+for Haskell's internal state monad (strict and lazy, respectively).
</para></listitem>
<listitem><para>
</para></listitem>
<listitem><para>
-Variables bound by a <literal>let</literal> statement in an <literal>mdo</literal>
-are monomorphic in the <literal>mdo</literal> (Section 3.1 of the paper). However
-GHC breaks the <literal>mdo</literal> into segments to enhance polymorphism,
-and improve termination (Section 3.2 of the paper).
+Similar to let-bindings, GHC implements the segmentation technique described in Section 3.2 of
+<ulink url="http://citeseer.ist.psu.edu/erk02recursive.html">A recursive do for Haskell</ulink>,
+to break up a single <literal>rec</literal> statement into a sequenc e of statements with
+<literal>rec</literal> groups of minimal size. This
+improves polymorphism, and reduces the size of the recursive "knot".
</para></listitem>
</itemizedlist>
</para>
+</sect3>
+
+<sect3> <title Mdo-notation (deprecated) </title>
+<para> GHC used to support the flag <option>-XREecursiveDo</option>,
+which enabled the keyword <literal>mdo</literal>, precisely as described in
+<ulink url="http://citeseer.ist.psu.edu/erk02recursive.html">A recursive do for Haskell</ulink>,
+but this is now deprecated. Instead of <literal>mdo { Q; e }</literal>, write
+<literal>do { rec Q; e }</literal>.
+</para>
<para>
Historical note: The old implementation of the mdo-notation (and most
of the existing documents) used the name
<literal>MonadRec</literal> for the class and the corresponding library.
This name is not supported by GHC.
</para>
+</sect3>
</sect2>
<indexterm><primary><literal>forall</literal></primary></indexterm>
</term>
<listitem><para>
- Stolen (in types) by: <option>-XScopedTypeVariables</option>,
+ Stolen (in types) by: <option>-XExplicitForAll</option>, and hence by
+ <option>-XScopedTypeVariables</option>,
<option>-XLiberalTypeSynonyms</option>,
<option>-XRank2Types</option>,
<option>-XRankNTypes</option>,
<sect3>
<title>Multi-parameter type classes</title>
<para>
-Multi-parameter type classes are permitted. For example:
+Multi-parameter type classes are permitted, with flag <option>-XMultiParamTypeClasses</option>.
+For example:
<programlisting>
</para>
</sect3>
-<sect3>
+<sect3 id="superclass-rules">
<title>The superclasses of a class declaration</title>
<para>
-There are no restrictions on the context in a class declaration
-(which introduces superclasses), except that the class hierarchy must
-be acyclic. So these class declarations are OK:
+In Haskell 98 the context of a class declaration (which introduces superclasses)
+must be simple; that is, each predicate must consist of a class applied to
+type variables. The flag <option>-XFlexibleContexts</option>
+(<xref linkend="flexible-contexts"/>)
+lifts this restriction,
+so that the only restriction on the context in a class declaration is
+that the class hierarchy must be acyclic. So these class declarations are OK:
<programlisting>
<sect3><title>Rules for functional dependencies </title>
<para>
In a class declaration, all of the class type variables must be reachable (in the sense
-mentioned in <xref linkend="type-restrictions"/>)
+mentioned in <xref linkend="flexible-contexts"/>)
from the free variables of each method type.
For example:
<sect1 id="other-type-extensions">
<title>Other type system extensions</title>
-<sect2 id="type-restrictions">
-<title>Type signatures</title>
+<sect2 id="explicit-foralls"><title>Explicit universal quantification (forall)</title>
+<para>
+Haskell type signatures are implicitly quantified. When the language option <option>-XExplicitForAll</option>
+is used, the keyword <literal>forall</literal>
+allows us to say exactly what this means. For example:
+</para>
+<para>
+<programlisting>
+ g :: b -> b
+</programlisting>
+means this:
+<programlisting>
+ g :: forall b. (b -> b)
+</programlisting>
+The two are treated identically.
+</para>
+<para>
+Of course <literal>forall</literal> becomes a keyword; you can't use <literal>forall</literal> as
+a type variable any more!
+</para>
+</sect2>
+
-<sect3 id="flexible-contexts"><title>The context of a type signature</title>
+<sect2 id="flexible-contexts"><title>The context of a type signature</title>
<para>
The <option>-XFlexibleContexts</option> flag lifts the Haskell 98 restriction
that the type-class constraints in a type signature must have the
g :: Eq [a] => ...
g :: Ord (T a ()) => ...
</programlisting>
+The flag <option>-XFlexibleContexts</option> also lifts the corresponding
+restriction on class declarations (<xref linkend="superclass-rules"/>) and instance declarations
+(<xref linkend="instance-rules"/>).
</para>
+
<para>
GHC imposes the following restrictions on the constraints in a type signature.
Consider the type:
language omits them; in Haskell 98, all the free type variables of an
explicit source-language type signature are universally quantified,
except for the class type variables in a class declaration. However,
-in GHC, you can give the foralls if you want. See <xref linkend="universal-quantification"/>).
+in GHC, you can give the foralls if you want. See <xref linkend="explicit-foralls"/>).
</para>
<para>
</orderedlist>
</para>
-</sect3>
-
-
</sect2>
</title>
<para>
-Haskell type signatures are implicitly quantified. The new keyword <literal>forall</literal>
-allows us to say exactly what this means. For example:
-</para>
-<para>
-<programlisting>
- g :: b -> b
-</programlisting>
-means this:
-<programlisting>
- g :: forall b. (b -> b)
-</programlisting>
-The two are treated identically.
-</para>
-
-<para>
-However, GHC's type system supports <emphasis>arbitrary-rank</emphasis>
+GHC's type system supports <emphasis>arbitrary-rank</emphasis>
explicit universal quantification in
types.
For example, all the following types are legal:
</itemizedlist>
</para></listitem>
</itemizedlist>
-Of course <literal>forall</literal> becomes a keyword; you can't use <literal>forall</literal> as
-a type variable any more!
</para>
</para>
</sect2>
+<sect2 id="mono-local-binds">
+<title>Monomorphic local bindings</title>
+<para>
+We are actively thinking of simplifying GHC's type system, by <emphasis>not generalising local bindings</emphasis>.
+The rationale is described in the paper
+<ulink url="http://research.microsoft.com/~simonpj/papers/constraints/index.htm">Let should not be generalised</ulink>.
+</para>
+<para>
+The experimental new behaviour is enabled by the flag <option>-XMonoLocalBinds</option>. The effect is
+that local (that is, non-top-level) bindings without a type signature are not generalised at all. You can
+think of it as an extreme (but much more predictable) version of the Monomorphism Restriction.
+If you supply a type signature, then the flag has no effect.
+</para>
+</sect2>
+
</sect1>
<!-- ==================== End of type system extensions ================= -->
have type <literal>Q Exp</literal></para></listitem>
<listitem><para> an type; the spliced expression must
have type <literal>Q Typ</literal></para></listitem>
- <listitem><para> a list of top-level declarations; the spliced expression must have type <literal>Q [Dec]</literal></para></listitem>
+ <listitem><para> a list of top-level declarations; the spliced expression
+ must have type <literal>Q [Dec]</literal></para></listitem>
</itemizedlist>
- </para>
Inside a splice you can can only call functions defined in imported modules,
- not functions defined elsewhere in the same module.</listitem>
-
+ not functions defined elsewhere in the same module.</para></listitem>
<listitem><para>
A expression quotation is written in Oxford brackets, thus:
A quasi-quotation can appear in either a pattern context or an
expression context and is also written in Oxford brackets:
<itemizedlist>
- <listitem><para> <literal>[:<replaceable>varid</replaceable>| ... |]</literal>,
+ <listitem><para> <literal>[$<replaceable>varid</replaceable>| ... |]</literal>,
where the "..." is an arbitrary string; a full description of the
quasi-quotation facility is given in <xref linkend="th-quasiquotation"/>.</para></listitem>
</itemizedlist></para></listitem>
</para>
</listitem>
+ <listitem><para> You may omit the <literal>$(...)</literal> in a top-level declaration splice.
+ Simply writing an expression (rather than a declaration) implies a splice. For example, you can write
+<programlisting>
+module Foo where
+import Bar
+
+f x = x
+
+$(deriveStuff 'f) -- Uses the $(...) notation
+
+g y = y+1
+
+deriveStuff 'g -- Omits the $(...)
+
+h z = z-1
+</programlisting>
+ This abbreviation makes top-level declaration slices quieter and less intimidating.
+ </para></listitem>
+
</itemizedlist>
(Compared to the original paper, there are many differences of detail.