|
| |
| Navigation |
Synopsis Defines a concrete syntax for Exp with layout.
Description In Rascal, the major difference between lexical syntax and non-lexical syntax is that:
Exp in Exp/Concrete/NoLayout with a layout definition:
module demo::lang::Exp::Concrete::WithLayout::Syntax layout Whitespace = [\t-\n\r\ ]*;Using the layout definition ( ), we define that the Whitespace non-terminal is used in between every symbol of the syntax productions in the current module.
And now we can use spaces in our definition of the eval function as well: module demo::lang::Exp::Concrete::WithLayout::Eval
import demo::lang::Exp::Concrete::WithLayout::Syntax;
import String;
import ParseTree;
public int eval(str txt) = eval(parse(#Exp, txt));
public int eval((Exp)`<IntegerLiteral l>`) = toInt("<l>");
public int eval((Exp)`<Exp e1> * <Exp e2>`) = eval(e1) * eval(e2);
public int eval((Exp)`<Exp e1> + <Exp e2>`) = eval(e1) + eval(e2);
public int eval((Exp)`( <Exp e> )`) = eval(e);
public value main(list[value] args) {
return eval("2+3");
}
Note that Rascal:PatternMatching will ignore all trees in layout positions, such that the parse tree of "1 + \n1" will match against <Exp e1> + <Exp e2>. The same goes for equality on parse trees.
For the above example Rascal will insert the Whitespace non-terminal that is defined at between every element of the syntax rules for Exp. Moreover, for the start production (See Exp/Concrete/NoLayout) Whitespace will be added before and after the Exp.
Examples The effect of the layout definition is that before parser generation the following grammar is derived for
Exp:
syntax Exp
= IntegerLiteral
| bracket "(" Whitespace Exp Whitespace ")"
> left Exp Whitespace "*" Whitespace Exp
> left Exp Whitespace "+" Whitespace Exp
;
syntax start[Exp] = Whitespace Exp top Whitespace;
To put this all to the test:
rascal>import demo::lang::Exp::Concrete::WithLayout::Syntax; ok rascal>import demo::lang::Exp::Concrete::WithLayout::Eval; ok rascal>eval("2 + 3"); int: 5 rascal>eval("2 + 3*4"); int: 14 rascal>eval("( 2+3 )* 4"); int: 20
Pitfalls
|