# HG changeset patch # User Adam Chlipala # Date 1217363895 14400 # Node ID a158f8c5aa5593cb49eb3ad0eef28aab0c025b4a # Parent 2232ab355f6651465721a30932bf67374dd045cc Parsing basic patterns diff -r 2232ab355f66 -r a158f8c5aa55 src/elaborate.sml --- a/src/elaborate.sml Tue Jul 29 16:02:02 2008 -0400 +++ b/src/elaborate.sml Tue Jul 29 16:38:15 2008 -0400 @@ -1137,6 +1137,8 @@ in ((L'.EFold dom, loc), foldType (dom, loc), []) end + + | L.ECase _ => raise Fail "Elaborate ECase" end diff -r 2232ab355f66 -r a158f8c5aa55 src/lacweb.grm --- a/src/lacweb.grm Tue Jul 29 16:02:02 2008 -0400 +++ b/src/lacweb.grm Tue Jul 29 16:38:15 2008 -0400 @@ -51,6 +51,7 @@ | FN | PLUSPLUS | MINUSMINUS | DOLLAR | TWIDDLE | STRUCTURE | SIGNATURE | STRUCT | SIG | END | FUNCTOR | WHERE | EXTERN | INCLUDE | OPEN | CONSTRAINT | CONSTRAINTS | EXPORT + | CASE | XML_BEGIN of string | XML_END | NOTAGS of string @@ -99,6 +100,11 @@ | tag of string * exp | tagHead of string * exp + | branch of pat * exp + | branchs of (pat * exp) list + | pat of pat + | pterm of pat + | attrs of (con * exp) list | attr of con * exp | attrv of exp @@ -310,6 +316,7 @@ | LPAREN eexp RPAREN DCOLON cexp (EAnnot (eexp, cexp), s (LPARENleft, cexpright)) | eexp MINUSMINUS cexp (ECut (eexp, cexp), s (eexpleft, cexpright)) + | CASE eexp OF barOpt branch branchs (ECase (eexp, branch :: branchs), s (CASEleft, branchsright)) eterm : LPAREN eexp RPAREN (#1 eexp, s (LPARENleft, RPARENright)) @@ -330,6 +337,19 @@ (EPrim (Prim.String ""), s (XML_BEGINleft, XML_ENDright))), s (XML_BEGINleft, XML_ENDright)) +branch : pat DARROW eexp (pat, eexp) + +branchs: ([]) + | BAR branch branchs (branch :: branchs) + +pat : pterm (pterm) + | cpath pterm (PCon (#1 cpath, #2 cpath, SOME pterm), s (cpathleft, ptermright)) + +pterm : SYMBOL (PVar SYMBOL, s (SYMBOLleft, SYMBOLright)) + | cpath (PCon (#1 cpath, #2 cpath, NONE), s (cpathleft, cpathright)) + | UNDER (PWild, s (UNDERleft, UNDERright)) + | LPAREN pat RPAREN (pat) + rexp : ([]) | ident EQ eexp ([(ident, eexp)]) | ident EQ eexp COMMA rexp ((ident, eexp) :: rexp) diff -r 2232ab355f66 -r a158f8c5aa55 src/lacweb.lex --- a/src/lacweb.lex Tue Jul 29 16:02:02 2008 -0400 +++ b/src/lacweb.lex Tue Jul 29 16:38:15 2008 -0400 @@ -259,6 +259,7 @@ "and" => (Tokens.AND (pos yypos, pos yypos + size yytext)); "fn" => (Tokens.FN (pos yypos, pos yypos + size yytext)); "fold" => (Tokens.FOLD (pos yypos, pos yypos + size yytext)); + "case" => (Tokens.CASE (pos yypos, pos yypos + size yytext)); "structure" => (Tokens.STRUCTURE (pos yypos, pos yypos + size yytext)); "signature" => (Tokens.SIGNATURE (pos yypos, pos yypos + size yytext)); diff -r 2232ab355f66 -r a158f8c5aa55 src/source.sml --- a/src/source.sml Tue Jul 29 16:02:02 2008 -0400 +++ b/src/source.sml Tue Jul 29 16:38:15 2008 -0400 @@ -89,6 +89,13 @@ withtype sgn_item = sgn_item' located and sgn = sgn' located +datatype pat' = + PWild + | PVar of string + | PCon of string list * string * pat option + +withtype pat = pat' located + datatype exp' = EAnnot of exp * con @@ -105,6 +112,8 @@ | ECut of exp * con | EFold + | ECase of exp * (pat * exp) list + withtype exp = exp' located datatype decl' = diff -r 2232ab355f66 -r a158f8c5aa55 src/source_print.sml --- a/src/source_print.sml Tue Jul 29 16:02:02 2008 -0400 +++ b/src/source_print.sml Tue Jul 29 16:38:15 2008 -0400 @@ -162,6 +162,17 @@ CName s => string s | _ => p_con all +fun p_pat' par (p, _) = + case p of + PWild => string "_" + | PVar s => string s + | PCon (ms, x, NONE) => p_list_sep (string ".") string (ms @ [x]) + | PCon (ms, x, SOME p) => parenIf par (box [p_list_sep (string ".") string (ms @ [x]), + space, + p_pat' true p]) + +val p_pat = p_pat' false + fun p_exp' par (e, _) = case e of EAnnot (e, t) => box [string "(", @@ -239,6 +250,19 @@ p_con' true c]) | EFold => string "fold" + | ECase (e, pes) => parenIf par (box [string "case", + space, + p_exp' false e, + space, + string "of", + space, + p_list_sep (box [space, string "|", space]) + (fn (p, e) => box [p_pat p, + space, + string "=>", + space, + p_exp e]) pes]) + and p_exp e = p_exp' false e fun p_datatype (x, cons) = diff -r 2232ab355f66 -r a158f8c5aa55 tests/case.lac --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/tests/case.lac Tue Jul 29 16:38:15 2008 -0400 @@ -0,0 +1,12 @@ +datatype t = A | B + +val swap = fn x : t => case x of A => B | B => A + +datatype u = C of t | D + +val out = fn x : u => case x of C y => y | D => A + +datatype nat = O | S of nat + +val is_two = fn x : int_list => + case x of S (S O) => A | _ => B