创建 LL(1) 语法的问题

Issue creating LL(1) grammar

我正在通过创建一个简单的递归下降解析器来学习解析器的工作原理。但是,我在将语法定义为 LL(1) 时遇到问题。我希望能够解析以下两个语句:

a = 1
a + 1

为此,我创建了以下语法规则:

statement:  assignent | expression
assignment: NAME EQUALS expression
expression: term [(PLUS|MINUS) term]
term:       NAME | NUMBER

然而,这会导致在使用 LL(1) 解析器时出现歧义,因为当在 statement 规则中遇到 NAME 标记时,它不知道它是 assignment 还是expression 没有前瞻性。

Python 的语法是 LL(1),所以我知道这是可能的,但我不知道该怎么做。我查看了 Python 在此处找到的语法规则 (https://docs.python.org/3/reference/grammar.html),但我仍然不确定它们是如何实现的。

任何帮助将不胜感激:)

就把=当作一个优先级很低的运算符。但是(除非你想要像 C 这样的语言,其中 = 确实是一个优先级非常低的运算符),你需要将它从内部(例如括号)表达式中排除。

如果你只有乘法和加法,你可以使用:

expression: factor ['+' factor]
factor:     term ['*' term]
term:       ID | NUMBER | '(' expression ')'

这是运算符优先级的指南: 具有更高的优先级,因为 + 的参数可以包括 s 但反之则不然。所以我们可以添加赋值:

statement: expression ['=' expression]

不幸的是,这将允许,例如:

(a + 1) = b

这是不可取的。所以它需要被消除,但是当生产被接受时(通过检查第一个 expression 的形式)而不是在语法本身中消除它是可能的。据我了解,这就是 Python 解析器所做的;查看关于 test 和关键字的长评论。

如果您改用 LR(1) 解析器,就不会遇到此问题。