[project @ 2004-06-23 22:43:20 by ross]
authorross <unknown>
Wed, 23 Jun 2004 22:43:21 +0000 (22:43 +0000)
committerross <unknown>
Wed, 23 Jun 2004 22:43:21 +0000 (22:43 +0000)
arrow notation fixes (problems reported bu John Hughes):

* allow an infixexp (exp0) to the left of -<.  This adds 4 more
  shift/reduce conflicts, because it makes if/lambda/let/case/proc
  before -< ambiguous.  This is the same sort of thing as
  "if x then y else z + 1", and as there shifting does the right thing.

* described the grammar more precisely

* fixed an example

merge to STABLE

ghc/compiler/parser/Parser.y.pp
ghc/docs/users_guide/glasgow_exts.sgml

index 5cc1ca8..4f7890d 100644 (file)
@@ -59,6 +59,9 @@ Conflicts: 29 shift/reduce, [SDM 19/9/2002]
 1 for ambiguity in 'if x then y else z :: T'           [State 136]
        (shift parses as 'if x then y else (z :: T)', as per longest-parse rule)
 
+4 for ambiguity in 'if x then y else z -< e'
+       (shift parses as 'if x then y else (z -< T)', as per longest-parse rule)
+
 8 for ambiguity in 'e :: a `b` c'.  Does this mean     [States 160,246]
        (e::a) `b` c, or 
        (e :: (a `b` c))
@@ -978,10 +981,10 @@ sigdecl :: { Located (OrdList (LHsDecl RdrName)) }
 
 exp   :: { LHsExpr RdrName }
        : infixexp '::' sigtype         { LL $ ExprWithTySig $1 $3 }
-       | fexp '-<' exp         { LL $ HsArrApp $1 $3 placeHolderType HsFirstOrderApp True }
-       | fexp '>-' exp         { LL $ HsArrApp $3 $1 placeHolderType HsFirstOrderApp False }
-       | fexp '-<<' exp        { LL $ HsArrApp $1 $3 placeHolderType HsHigherOrderApp True }
-       | fexp '>>-' exp        { LL $ HsArrApp $3 $1 placeHolderType HsHigherOrderApp False}
+       | infixexp '-<' exp             { LL $ HsArrApp $1 $3 placeHolderType HsFirstOrderApp True }
+       | infixexp '>-' exp             { LL $ HsArrApp $3 $1 placeHolderType HsFirstOrderApp False }
+       | infixexp '-<<' exp            { LL $ HsArrApp $1 $3 placeHolderType HsHigherOrderApp True }
+       | infixexp '>>-' exp            { LL $ HsArrApp $3 $1 placeHolderType HsHigherOrderApp False}
        | infixexp                      { $1 }
 
 infixexp :: { LHsExpr RdrName }
index 626cfdd..30de1d2 100644 (file)
@@ -3483,31 +3483,46 @@ using combinators from the
 module.
 </para>
 
-<para>The extension adds a new kind of expression for defining arrows,
-of the form <literal>proc pat -> cmd</literal>,
+<para>The extension adds a new kind of expression for defining arrows:
+<screen>
+<replaceable>exp</replaceable><superscript>10</superscript> ::= ...
+       |  proc <replaceable>apat</replaceable> -> <replaceable>cmd</replaceable>
+</screen>
 where <literal>proc</literal> is a new keyword.
 The variables of the pattern are bound in the body of the 
 <literal>proc</literal>-expression,
 which is a new sort of thing called a <firstterm>command</firstterm>.
 The syntax of commands is as follows:
 <screen>
-cmd   ::= exp1 -&lt;  exp2
-       |  exp1 -&lt;&lt; exp2
-       |  do { cstmt1 .. cstmtn ; cmd }
-       |  let decls in cmd
-       |  if exp then cmd1 else cmd2
-       |  case exp of { calts }
-       |  cmd1 qop cmd2
-       |  (| aexp cmd1 .. cmdn |)
-       |  \ pat1 .. patn -> cmd
-       |  cmd aexp
-       |  ( cmd )
-
-cstmt ::= let decls
-       |  pat &lt;- cmd
-       |  rec { cstmt1 .. cstmtn }
-       |  cmd
+<replaceable>cmd</replaceable>   ::= <replaceable>exp</replaceable><superscript>10</superscript> -&lt;  <replaceable>exp</replaceable>
+       |  <replaceable>exp</replaceable><superscript>10</superscript> -&lt;&lt; <replaceable>exp</replaceable>
+       |  <replaceable>cmd</replaceable><superscript>0</superscript>
+</screen>
+with <replaceable>cmd</replaceable><superscript>0</superscript> up to
+<replaceable>cmd</replaceable><superscript>9</superscript> defined using
+infix operators as for expressions, and
+<screen>
+<replaceable>cmd</replaceable><superscript>10</superscript> ::= \ <replaceable>apat</replaceable> ... <replaceable>apat</replaceable> -> <replaceable>cmd</replaceable>
+       |  let <replaceable>decls</replaceable> in <replaceable>cmd</replaceable>
+       |  if <replaceable>exp</replaceable> then <replaceable>cmd</replaceable> else <replaceable>cmd</replaceable>
+       |  case <replaceable>exp</replaceable> of { <replaceable>calts</replaceable> }
+       |  do { <replaceable>cstmt</replaceable> ; ... <replaceable>cstmt</replaceable> ; <replaceable>cmd</replaceable> }
+       |  <replaceable>fcmd</replaceable>
+
+<replaceable>fcmd</replaceable>  ::= <replaceable>fcmd</replaceable> <replaceable>aexp</replaceable>
+       |  ( <replaceable>cmd</replaceable> )
+       |  (| <replaceable>aexp</replaceable> <replaceable>cmd</replaceable> ... <replaceable>cmd</replaceable> |)
+
+<replaceable>cstmt</replaceable> ::= let <replaceable>decls</replaceable>
+       |  <replaceable>pat</replaceable> &lt;- <replaceable>cmd</replaceable>
+       |  rec { <replaceable>cstmt</replaceable> ; ... <replaceable>cstmt</replaceable> [;] }
+       |  <replaceable>cmd</replaceable>
 </screen>
+where <replaceable>calts</replaceable> are like <replaceable>alts</replaceable>
+except that the bodies are commands instead of expressions.
+</para>
+
+<para>
 Commands produce values, but (like monadic computations)
 may yield more than one value,
 or none, and may do other things as well.
@@ -3692,7 +3707,7 @@ ArrowChoice a => (&lt;+>) :: a e c -> a e c -> a e c
 </programlisting>
 so we can use it to build commands:
 <programlisting>
-expr' = proc x ->
+expr' = proc x -> do
                 returnA -&lt; x
         &lt;+> do
                 symbol Plus -&lt; ()
@@ -3703,6 +3718,9 @@ expr' = proc x ->
                 y &lt;- term -&lt; ()
                 expr' -&lt; x - y
 </programlisting>
+(The <literal>do</literal> on the first line is needed to prevent the first
+<literal>&lt;+> ...</literal> from being interpreted as part of the
+expression on the previous line.)
 This is equivalent to
 <programlisting>
 expr' = (proc x -> returnA -&lt; x)