I am currently stuck with a rule I am trying to parse using boost spirit x3. Here is the EBNF(using the % operator from spirit for lists) for what I am trying to parse:
type ::= class_type | lambda_type
lambda_type ::= more_arg_lambda | one_arg_lambda
more_arg_lambda ::= "(", type%",", ")", "=>", type
one_arg_lambda ::= type, "=>", type <- here is the left recursion
class_type ::= identifier%"::", ["<", type%",", ">"]
using boost spirit x3, I am trying to parse into the following struct/variant:
typedef x3::variant<
nil,
x3::forward_ast<LambdaType>,
x3::forward_ast<ClassType>
> Type;
struct LambdaType {
std::vector<Type> parameters_;
Type return_type_;
};
struct ClassType{
std::vector<std::string> name_;
std::vector<Type> template_args_;
};
I have a live example of what I am currently trying here, which is not working, I also tried to change the order of the variant parser, which doesn't help, I get endless recursion, or not the behavior I would expect(or wish).
Can anybody help me debugging this parser?
I think I have some type of left-recursion in the parser, is there a chance to avoid this or is there no chance to rewrite the grammar? Is this grammar even parseable with boost spirit x3?
EDIT:
I managed to eliminate the left recursion in this grammar. Now the grammar is the following:
type ::= class_type | lambda_type
lambda_type ::= more_arg_lambda | one_arg_lambda
more_arg_lambda ::= "(", type%",", ")", "=>", type
one_arg_lambda ::= class_type, "=>" type, A
| "(", type%",", ")", "=>", type, "=>", type, A
class_type ::= identifier%"::", ["<", type%",", ">"]
A::= "=>", type, A | eps
but now there is the next problem, how can I make boost spirit x3 to parse these rules into the given structs? I cannot imagine what the A
or the one_arg_lambda
parsers are returning now, the one_arg_lambda
parser should parse into a LambdaType
struct, but depending on what A
parses into that's not necessary true now. So the question is now, how can I get a non-left recursive parser, which parses the grammar above into my structs using boost-spirit-x3?
EDIT II:
I would like =>
to be right associative so foo => bar => baz => baham
means foo => (bar => (baz => bahama))
foo => bar => baz
to mean?( foo => bar ) => baz
orfoo => ( bar => baz )
? – Almsmanfoo=>(bar=>baz)
– Aerogram