Spirit: how to force backtracking
I have the following grammar rule: value = (int_ % ',') | *ascii::print; The intention is to parse either a comma-separated list of integers or a string. The rule as such fails in cases like "123ABC", which should be parsed as string.
From the description of the | operator, I would expect the parser to backtrack and try the other alternative when it sees that the first alternative does not match the input. However, I get a parse error instead (this rule is a part of a larger grammar), I guess because the first alternative matches the single integer but the rest of the grammar cannot be matched.
How to rewrite the grammar to resolve this ambiguity, or force spirit to backtrack if the first alternative of 'value' cannot be matched?
On 11/03/2017 05:20 AM, Stian Zeljko Vrba via Boost-users wrote:
I have the following grammar rule:
value = (int_ % ',') | *ascii::print;
The intention is to parse either a comma-separated list of integers or a string. The rule as such fails in cases like "123ABC", which should be parsed as string. From the description of the | operator, I would expect the parser to backtrack and try the other alternative when it sees that the first alternative does not match the input. However, I get a parse error instead (this rule is a part of a larger grammar), I guess because the first alternative matches the single integer but the rest of the grammar cannot be matched.
How to rewrite the grammar to resolve this ambiguity, or force spirit to backtrack if the first alternative of 'value' cannot be matched?
What happens when you reverse the order of the alternatives: value = *ascii::print | (int_ % ',');
On Fri, Nov 3, 2017 at 8:20 AM, Stian Zeljko Vrba via Boost-users
I have the following grammar rule:
value = (int_ % ',') | *ascii::print;
The intention is to parse either a comma-separated list of integers or a string. The rule as such fails in cases like "123ABC", which should be parsed as string. From the description of the | operator, I would expect the parser to backtrack and try the other alternative when it sees that the first alternative does not match the input. However, I get a parse error instead (this rule is a part of a larger grammar), I guess because the first alternative matches the single integer but the rest of the grammar cannot be matched.
How to rewrite the grammar to resolve this ambiguity, or force spirit to backtrack if the first alternative of 'value' cannot be matched?
It seems that "123" is a valid comma-separated list of integers (with 1 integer) which gets matched. Maybe you could use an eps rule to match a separator without consuming the input.
Boost-users mailing list Boost-users@lists.boost.org https://lists.boost.org/mailman/listinfo.cgi/boost-users
Regards, -- Felipe Magno de Almeida
It seems that "123" is a valid comma-separated list of integers (with 1 integer) which gets matched. Maybe you could use an eps rule to match a separator without consuming the input.
Yes, that was the problem, so the first alternative matched and then the rest
of the grammar failed to parse. I managed to fix it with and-predicate like this:
my_int = int_ >> &(lit(',') | lit(':'))
where ',' is expected in the case of list whereas ':' comes from the
higher-level rule which uses my_int rule.
-- Stian
________________________________________
From: Felipe Magno de Almeida
I have the following grammar rule:
value = (int_ % ',') | *ascii::print;
The intention is to parse either a comma-separated list of integers or a string. The rule as such fails in cases like "123ABC", which should be parsed as string. From the description of the | operator, I would expect the parser to backtrack and try the other alternative when it sees that the first alternative does not match the input. However, I get a parse error instead (this rule is a part of a larger grammar), I guess because the first alternative matches the single integer but the rest of the grammar cannot be matched.
How to rewrite the grammar to resolve this ambiguity, or force spirit to backtrack if the first alternative of 'value' cannot be matched?
It seems that "123" is a valid comma-separated list of integers (with 1 integer) which gets matched. Maybe you could use an eps rule to match a separator without consuming the input.
Boost-users mailing list Boost-users@lists.boost.org https://lists.boost.org/mailman/listinfo.cgi/boost-users
Regards, -- Felipe Magno de Almeida
participants (3)
-
Felipe Magno de Almeida
-
Larry Evans
-
Stian Zeljko Vrba