This repository has been archived by the owner on Oct 28, 2023. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 9
Parsing DSL
Christophe VG edited this page Mar 6, 2017
·
1 revision
During the development of v1.1 a Fluid Parsing API, eliminating explicit try { ... } catch { ... }
-blocks was introduced to make the generated parsers more "human readable":
An example of a v1.0 generated parser:
public Program ParseProgram() {
Identifier identifier = null;
List<Assignment> assignments = new List<Assignment>();
this.Log("ParseProgram");
int pos = this.source.position;
try {
this.source.Consume("PROGRAM");
identifier = this.ParseIdentifier();
this.source.Consume("BEGIN");
{
Assignment temp;
while(true) {
try {
temp = this.ParseAssignment();
} catch(ParseException) {
break;
}
assignments.Add(temp);
}
}
this.source.Consume("END.");
} catch(ParseException e) {
this.source.position = pos;
throw this.source.GenerateParseException(
"Failed to parse Program.", e
);
}
return new Program() {
Identifier = identifier,
Assignments = assignments
};
}
In v1.1 this was implemented as such:
// program ::= "PROGRAM" identifier "BEGIN" { assignment } "END." ;
public Program ParseProgram() {
Program program = new Program();
this.Log( "ParseProgram" );
Parse( () => {
Consume("PROGRAM");
program.Identifier = ParseIdentifier();
Consume("BEGIN");
program.Assignments = Many<Assignment>(ParseAssignment);
Consume("END.");
}).OrThrow("Failed to parse Program");
return program;
}
Although it violates some of my personal code style rules, in this case the inner-DSL is dominant and requires as little as possible normal C# code ;-) The first results of this change are nice. I'm continuing to investigate possibilities down this road.