rust-peg的precedence!优先级问题:为何*优先级低于赋值=
问题原因分析
你遇到的结果不符合预期是由precedence!宏的使用错误导致的:
- 操作数的引用符号使用错误
在precedence!宏定义的规则中,@符号代表「当前优先级层级及更高优先级层级的表达式」,如果你直接写完整的规则名expr(),则代表匹配完整的expr规则,包含所有比当前层级优先级更低的表达式。
你在定义*解引用规则时,操作数写的是x:expr(),这就允许*的操作数包含优先级更低的=赋值表达式,解析*a = gg时会优先把*后面的整个a = gg识别为*的操作数,最终生成*assign(&mut a, gg)的结果。 - 优先级层级逻辑说明
你当前的层级顺序是符合预期的:precedence!中用--分割的层级从上到下优先级依次升高,你把=放在最上层、*放在下层,确实是*优先级高于=,这部分逻辑没有问题。
修复方案
只需要把*规则中的expr()改为@即可,修改后的expr规则如下:
rule expr() -> String = precedence! { variable:@ _ "=" _ value:(@) { format!("assign(&mut {}, {})", variable, value) } -- "*" _ x:@ { format!("*{}", x) } -- ident:ident() { String::from(ident) } }
修改后运行代码输入*a = gg,会输出你预期的assign(&mut *a, gg)。因为修改后*的操作数只能匹配优先级更高的*表达式或者ident,a被识别为*的操作数,整个*a再被识别为=的左值,符合正常的运算符优先级逻辑。
内容的提问来源于stack exchange,提问作者Doubtful
相关产品推荐
相关产品推荐

