ANTLR报告错误,我认为它应该能够通过回溯来解决输入

时间:2012-04-07 15:47:39

标签: antlr grammar backtracking

我有一个简单的语法,大部分都有效,但在一个地方报告错误,我认为不应该,因为它可以使用回溯来解决。

这是有问题的部分。

command: object message_chain;
object: ID;
message_chain: unary_message_chain keyword_message?
             | binary_message_chain keyword_message?
             | keyword_message;
unary_message_chain: unary_message+;
binary_message_chain: binary_message+;
unary_message: ID;
binary_message: BINARY_OPERATOR object;
keyword_message: (ID ':' object)+;

这是简化版本,对象更复杂(它可能是其他命令,原始值等的结果,但该部分工作正常)。问题出在message_chain,第一种选择。对于像obj unary1 unary2这样的输入,它可以正常工作,但是像obj unary1 unary2 keyword1:obj2这样的输入是将keyword1作为一元消息进行匹配,并在到达:时失败。我认为这种情况解析器会回溯并认为存在:并认识到这是关键字消息。

如果我将关键字消息设为非可选,它可以正常工作,但我需要关键字消息是可选的。

Parser在第二个备选(binary_message)和第三个备选(只是keyword_message)中找到关键字消息。所以这样的结果会产生很好的结果:1 + 2 + 3 Keyword1:Value

我错过了什么?在选项中将回溯设置为true,并且在其他情况下,它在同一语法中工作正常。

感谢。

1 个答案:

答案 0 :(得分:1)

这不是PEG式回溯的情况,因为失败时只返回到未完成的推导中的决策点。对于输入obj unary1 unary2 keyword1:obj2,使用单个标记预测,keyword1可以使用unary_message_chain。失败可能不会发生在keyword_message之前,接下来要尝试的是message_chain的第二个替代方法,即binary_message_chain,因此错过了正确的解析。

然而,由于此语法是LL(2),因此应该可以扩展前瞻以避免在keyword1内使用unary_message_chain。您是否尝试过明确设置k=2,而无需回溯?