通过跟随this question,我能够为我的解析器语法添加对交替字符(例如ababa
或baba
)的支持。
我现在希望通过允许重复字符来扩展它。
例如,我希望能够支持abaaabab
和aababaaa
。在我的特定情况下,只允许a
重复,但允许重复b
的解决方案也很有用。
根据另一个问题的规则:
expr ::= A | B
A ::= "a" B | "a"
B ::= "b" A | "b"
...我尝试将其扩展为支持重复,如下所示:
expr ::= A | B
# support 1 or more "a"
A_one_or_more = A_one_or_more "a" | "a"
A ::= A_one_or_more B | A_one_or_more
B ::= "b" A | "b"
......但那个语法含糊不清。是否可以明确这一点,如果是这样,任何人都可以帮我消除歧义吗?
我正在使用lemon parser这是一个LALR(1)解析器。
答案 0 :(得分:1)
这是一个在线检查语法的好工具http://smlweb.cpsc.ucalgary.ca/start.html。它实际上接受the grammar you provided作为有效的LALR(1)语法。
一个不同的LALR(1)语法,允许重新定义一个,将是:
S ::= "a" S | "a" | "b" A | "b"
A ::= "a" S .
答案 1 :(得分:1)
解析的重点一般是解析;也就是说,确定输入的句法结构。这与简单地验证输入属于某种语言有很大不同。
例如,可以使用正则表达式a
来描述由b
和(a|b)*
的任意重复组成的语言,该正则表达式可以用BNF编写为
S ::= /* empty */ | S a | S b
但这可能无法捕捉到你试图定义的句法结构。另一方面,由于您没有指定该结构,因此很难知道。
以下是一些构建不同解析树的可能性:
S ::= E | S E
E ::= A b | E b
A ::= a | A a
S ::= E | S E
E ::= A B
A ::= a | A a
B ::= b | B b
在编写语法来解析语言时,首先绘制您提出的解析树是很有用的。通常,您可以直接从树的形式编写语法,这表明正式语法主要是文档工具,因为它以非正式描述不能的方式清楚地描述语言。使用解析器生成器将该语法转换为解析器可确保解析器实现所描述的语言。或者,至少,这就是目标。