A Parsing Expression Grammar (PEG) module, using the D programming language.
Pegged is a parsing expression grammar (PEG) generator implemented in the D programming language.
The idea is to give the generator a PEG, with the syntax presented in the reference article . From this grammar definition a set of related parsers will be created, to be used at runtime or compile time.
To use Pegged, just call the
grammarfunction with a PEG and mix it in. For example:
import pegged.grammar;mixin(grammar(` Arithmetic: Term < Factor (Add / Sub)* Add < "+" Factor Sub < "-" Factor Factor < Primary (Mul / Div)* Mul < "*" Primary Div < "/" Primary Primary < Parens / Neg / Pos / Number / Variable Parens < "(" Term ")" Neg < "-" Primary Pos < "+" Primary Number < ~([0-9]+)
Variable
This creates the
Arithmeticgrammar, with theExpr,Add,Factor(and so on) rules for basic arithmetic expressions with operator precedence ('*' and '/' bind stronger than '+' or '-').identifieris a pre-defined parser recognizing your basic C-style identifier (first a letter or underscore, then digits, letters or underscores). In the rest of this document, I'll call 'rule' aParser expression and I'll use 'grammar' to designate the entire group of rules given togrammar.To use a grammar, call it with a string. It will return a parse tree containing the calls to the different rules:
// Parsing at compile-time: enum parseTree1 = Arithmetic("1 + 2 - (3*x-5)*6");pragma(msg, parseTree1.matches); assert(parseTree1.matches == ["1", "+", "2", "-", "(", "3", "", "x", "-", "5", ")", "", "6"]); writeln(parseTree1);
// And at runtime too: auto parseTree2 = Arithmetic(" 0 + 123 - 456 "); assert(parseTree2.matches == ["0", "+", "123", "-", "456"]);
Even for such a simple grammar and such a simple expression, the resulting parse tree is a bit long to be shown here. See the result here
By default, the grammars do not silently consume spaces, as this is the standard behaviour for PEGs. There is an opt-out though, with the simple
<arrow instead of(you can see it in the previous example).How to get Pegged
Pegged is a github project, hosted at https://github.com/PhilippeSigaud/Pegged
To get it:
$ git clone https://github.com/PhilippeSigaud/PeggedThe
/docsdirectory contains an empty/wikidirectory, linked to the github wiki as a git submodule. Here is how to get it:$ cd $ git submodule init $ git submodule updateThis should give you a
/docs/wikidirectory full of markdown files, right from the online wiki.Tutorial and docs
The Pegged wiki is here. It contains a growing tutorial. All the wiki pages are also present (as Markdown files) in the
docsdirectory.Features
mixin(grammar(rules));in a module and then grammars and rules can refer to one another. That way, you can have utility grammars providing their functionalities to other grammars. Grammar Composition
asModule(string moduleName, string gram)function in
pegged.grammarto do that. See Grammars as Modules.
More advanced features, outside the standard PEG perimeter are there to bring more power in the mix:
"List(E, Sep) is possible. The previous rule defines a parametrized parser taking two other parsers (namely,EandSep) to match aSep-separated list ofE's. Entire grammars can be parametrized, too. See Parametrized Rules to see what's possible.
Articles:
D Code:
Other languages:
Pegged is released with the Boost license (like most D projects). See here for more details.