-
Notifications
You must be signed in to change notification settings - Fork 35
EBNF parser
you can use EBNF notation :
- '*' to repeat 0 or more the same terminal or non terminal
- '+' to repeat once or more the same terminal or non terminal
for repeated elements values passed to [Production]
methods are :
-
List<TOut>
for a repeated non terminal -
List<Token<TIn>>
for a repeated terminal
[Production("listElements: value additionalValue*")]
public JSon listElements(JSon head, List<JSon> tail)
{
JList values = new JList(head);
values.AddRange(tail);
return values;
}
See EBNFJsonParser.cs for a complete EBNF json parser.
the '?' modifier allow optional token or non-erminal.
- for tokens the
Token<TIn>
parameter has aIsEmpty
property set totrue
when the matching token is absent. - for nonterminal the visitor method get an
OptionValue<TOut>
instead of TOut. Then the parameter can be tested for emptyness with IsNone property.
//option token
[Production("block: A B? C")]
public AST listElements(Token<TIn>, a Token<TIn> b, Token<TIn> c)
{
if (b.IsEmpty) {
// do something usefull
}
else {
string bValue = b.Value;
// do other thing still usefull
}
}
// optional non terminal
[Production("root2 : a B? c ")]
public string root2(Token<OptionTestToken> a, ValueOption<string> b, Token<OptionTestToken> c)
{
StringBuilder r = new StringBuilder();
r.Append($"R(");
r.Append(a.Value);
r.Append(b.Match(v => $",{v}", () => ",<none>"));
r.Append($",{c.Value}");
r.Append($")");
return r.ToString();
}
Sometimes tokens does not bring any semantic value. For example in C like language, brackets ('{') only denotes beginning of blocks but does add any other information. Their only use is to guide the syntax parser.
So we proposed a way to dismiss this tokens on the visitor methods.
the [d]
(d for discard) modifier marks a token as ignored.
here is an exemple for a C block statement:
[Production("block: LBRACKET [d] statement* RBRACKET [d]")]
public AST listElements( List<AST> statements)
{
// any usefull code
}
The EBNF notation has been implemented in CSLY using the BNF notation. The EBNF parser builder is built using the BNF parser builder. Incidently the EBNF parser builder is a good and complete example for BNF parser : RuleParser.cs