0

我正在学习 ANTLR4,我一度感到困惑。对于类似 Java 的语言,我正在尝试为成员链等结构添加规则,如下所示:

expr1.MethodCall(expr2).MethodCall(expr3);

我收到一个错误,说我的两个规则是相互左递归的:

expression
    : literal
    | variableReference
    | LPAREN expression RPAREN
    | statementExpression
    | memberAccess
    ;

memberAccess: expression DOT (methodCall | fieldReference);

我想我明白为什么上述规则组合被认为是左递归的:因为memberAccess是的候选者expression并且memberAccessexpression.

但是,当我看到(通过查看Java 示例)如果我只是将 to 的内容移动memberAccessexpressionANTLR4 时,我的理解就崩溃了(即使它仍然没有解析我想要的内容,似乎陷入了一个循环):

expression
    : literal
    | variableReference
    | LPAREN expression RPAREN
    | statementExpression
    | expression DOT (methodCall | fieldReference)
    ;
  1. 为什么第一个例子是左递归的,而第二个不是?
  2. 我该怎么做才能真正解析初始行?
4

2 回答 2

1

第二个是左递归但不相互左递归。ANTLR4 可以使用内置算法消除左递归规则。它不能消除互左递归规则。可能存在一种算法,但这几乎不会保留动作和语义谓词。

于 2015-04-01T16:12:00.400 回答
0

出于某种原因,当我的语法有左递归时,ANTLRWorks 2 没有响应,导致我(错误地)认为我的语法是错误的。

从命令行编译和测试表明,具有立即左递归的版本实际上可以正确编译和解析。

(我把它留在这里,以防其他人对 IDE 的行为感到困惑。)

于 2015-04-03T15:21:27.287 回答