Antlr:意想不到的行为

时间:2013-07-24 17:12:09

标签: antlr

为什么这个简单的语法

grammar Test;

expr
    :    Int | expr '+' expr;

Int
:    [0-9]+;

与输入1+1不匹配?它说“没有规则expr的方法或它有参数”但在我的选择中它应该匹配。

2 个答案:

答案 0 :(得分:3)

看起来我暂时没有使用过ANTLR ...... ANTLRv3 没有支持左递归规则but ANTLRv4 does support immediate left recursion。它还支持您在帖子中使用的类似于regex的字符类语法。我测试了这个版本,它适用于ANTLRWorks2(在ANTLR4上运行):

grammar Test;

start : expr
      ;
expr  : expr '+' expr
      | INT
      ;
INT   : [0-9]+
      ;

如果您添加start规则,则ANTLR可以推断EOF在该规则的末尾。它似乎无法推断EOF更复杂的规则,例如exprexpr2,因为它们是递归的...


下面有很多评论,所以这里是(ANTLR4的合着者)Sam Harwell的回应(重点补充):

  

您仍希望在开始规则中包含显式EOF。 OP直接使用expr所面临的问题是 ANTLR 4在内部将其重写为expr [int _p] (对于所有左递归规则都是如此),并且包含的​​ TestRig不能直接执行带参数的规则。添加启动规则可以解决问题,因为TestRig能够执行该规则。 :)

我发布了关于EOF的后续问题:When is EOF needed in ANTLR 4?

答案 1 :(得分:1)

如果您的命令如下所示:

grun MYGRAMMAR xxx -tokens

抛出此异常:

No method for rule xxx or it has arguments

然后,将使用您在上面的命令中指定的规则抛出此异常。这意味着该规则可能不存在。

System.err.println("No method for rule "+startRuleName+" or it has arguments");

因此startRuleName如果它不是语法中的第一个(开始)规则,则应打印xxx。将xxx作为语法中的第一条规则来防止这种情况发生。