【发布时间】:2013-05-25 00:16:28
【问题描述】:
我了解 ANTLR 可以接受 LL(*) 语法。但是,有没有办法使用 ANTLR 来检查语法是否是 LL(1)?
【问题讨论】:
我了解 ANTLR 可以接受 LL(*) 语法。但是,有没有办法使用 ANTLR 来检查语法是否是 LL(1)?
【问题讨论】:
options {
k = 1;
}
如果您的语法不在 LL(1) 中,它会发出警告。
【讨论】:
对于 LL(1) 的语法/语言,我们知道在输入中的任何给定位置,我们只能采用一种产生式来消耗输入的标记。因此,为了确定一个文法是否为 LL(1),我们需要:
1) 检查所有非终结符的第一组,如果单个非终结符中有任何重复,则语法不是 LL(1)。
例如:S->aba | abc (如果给定输入“a”,我们将使用哪个产生式,我们无法确定,需要查看下一个输入令牌,实际上我们需要查看第三个令牌才能确定(所以这个将需要 LL(3)。
2) 由于我们知道要为哪个非终结符寻找产生式,因此我们不需要考虑其他非终结符的第一组。
前任。 S->aba
T->acc
FIRST(s) 与 FIRST(T) = {a} 的交集,但由于我们知道我们正在为 S 或 T 生成(一次仅一个),我们不需要担心多个非终结符有非空相交套。
3) 最后,当文法转到空字符串 (S->ε) 时要小心。在这种情况下,应将 FOLLOW 集与 FIRST 联合,以确保它们的交集为空。
前任。 S->aba | bSa | ε
T->cdd
在这里,如果我们得到输入“ba...”,我们将使用产生式 S->bSa,但随后我们会在输入流中看到“a”并且不知道是否产生 S->aba(如果输入是 b[aba]a) 或产生 S->ε (如果输入是 b[ε]a)
【讨论】: