【问题标题】:Negative lookahead in LR parsing algorithmLR解析算法中的负前瞻
【发布时间】:2013-04-13 11:21:41
【问题描述】:

为 LR 系列解析生成器(例如 YACC、BISON 等)考虑这样的语法规则:

Nonterminal : [ lookahead not in {Terminal1, ..., TerminalN} ] Rule ;

这是一个普通的规则,除了它有一个限制:用这个规则产生的短语不能以Terminal1, ..., TerminalN开头。 (当然,这个规则可以用一套常用的规则来代替,但它会导致更大的语法)。这对于解决冲突很有用。

问题是,是否存在接受此类限制的 LR 表构造算法的修改?在我看来,这样的修改是可能的(如优先关系)。

当然,它可以在运行时检查,但我的意思是编译时检查(在构建解析表时执行的检查,如 yacc 中的 %prec%left%right%nonassoc 指令兼容的发电机。)

【问题讨论】:

    标签: parsing generator conflict resolve negative-lookahead


    【解决方案1】:

    我不明白为什么这是不可能的,但我也看不出有什么明显的理由说明它会有用。你有一个例子吗?

    最简单的方法是进行括号中提到的语法转换。这会产生更大的语法,但不会人为地增加 LR 状态的数量。

    基本的转变,只需要一点点挥手:

    对于任何有终端限制的生产:

    • 如果生产以不可为空的非终端开始,请将非终端替换为终端限制版本。

    • 如果生产以终端限制列表中的终端开始,则删除生产

    • 如果生产以不在终端限制列表中的终端开始,则无需更改。

    如果产生式以可空非终结符开头,则必须创建可空非终结符的两个版本,一个始终为空,另一个不可为空;然后创建两个版本的产品,一个从每个新的非终端开始。然后应用上述转换,但将“开始于”解释为“在任何始终为空的非终结符之后开始”。

    您实际上不需要修改语法,因为上述转换可以在底层 SLR 机器的构建过程中即时完成,至少对于 LR(0) 和 LALR(1) 构造来说是这样。

    【讨论】:

    • 感谢您的回答!是的,我有一个例子,它是 ECMA-262 语法(ecma-international.org/ecma-262/5.1,例如第 12.4 节)。由于该语法使用Expression 产生式有无限制,我们必须将描述Experssion 的语法部分加倍。在我的 LALR(1) 解析器生成器中,它会导致更多的状态(350 对 470)。保留 350 个状态并满足限制会非常好。
    猜你喜欢
    • 1970-01-01
    • 2012-12-15
    • 1970-01-01
    • 2016-07-27
    • 2018-03-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多