Parsing 如何将此语法转换为LR(1)?
我的语法与LR(1)冲突无法解决;然而,语法应该是明确的。我将首先用五个标记在简化语法上演示这个问题:Parsing 如何将此语法转换为LR(1)?,parsing,lr,Parsing,Lr,我的语法与LR(1)冲突无法解决;然而,语法应该是明确的。我将首先用五个标记在简化语法上演示这个问题:(,),{},,和id EBNF如下所示: args = ( id ',' )* expression = id | '(' expression ')' | '(' args ')' '{}' 语法是明确的,最多需要两个前瞻标记。当(移位时,只有五种可能: (→ 复发 )→ 减少为”('args')” id)不是{}→ 减少为”(“表
(
,)
,{}
,,
和id
EBNF如下所示:
args = ( id ',' )*
expression = id
| '(' expression ')'
| '(' args ')' '{}'
语法是明确的,最多需要两个前瞻标记。当(
移位时,只有五种可能:
(
→ 复发)
→ 减少为”('args')”
id
)
不是{}
→ 减少为”(“表达式”)”
id
)
{}
→ 减少为'('args')'{}'
id
,
→ 减少为('args')'{}'
(最终)然而,我不太明白在这种特殊情况下如何进行转换。请注意,上面的简化语法是从;特别是,是否可以在不触碰
expr
和上面的所有内容的情况下转换主
。基本思想是将(id)
案例与其他两种可能性((expr\u not\u id)
和(列出至少两个id)
)分开。然后,关于如何减少(id)
的决定可以推迟到前瞻令牌可用为止(在您的情况下,{
,假设这足够了)
不幸的是,虽然将expr
转换为expr\u not\u id
非常简单,几乎是机械的,但它确实涉及到很多作品。而且,它有点难看。因此它无法解决您在最后一句中提出的问题。我实际上不认为有可能转换主要内容
没有触摸expr
,但我以前很惊讶
(另一个显而易见的解决方案,因为语法事实上是明确的,就是使用GLR解析器生成器,但我不相信您正在使用的解析器生成器具有该功能。)事实上,我刚刚得出了与您相同的结论。然而,我的解析器生成器(menhir)有更高阶的规则,所以我可以让它为我做繁重的工作。我可能会自己回答这个问题(如果它对我有效的话),很抱歉不接受!最有趣的是,我知道你链接的问题的作者。我刚完成了你的转换,它工作了,尽管需要对语法进行一系列奇怪的转换。太棒了。
formal_arg: Ident
{}
formal_args: formal_arg Comma formal_args
| formal_arg
| /* nothing */
{}
primary: Ident
| LParen formal_args Curly
| LParen primary RParen
{}