博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Bison 操作符前可以为空导致的归约/归约冲突
阅读量:3958 次
发布时间:2019-05-24

本文共 626 字,大约阅读时间需要 2 分钟。

今天遇见一个很奇怪的归约/归约冲突,大概类似这样:

...%left NOT AND...expr:     NUM    | expr opt AND expr    ;opt: NOT    | /* empty */    ;...

一直在报归约/归约冲突,我就懵了,哪里冲突了???

直到我仔细研读了一波output文件才弄明白:

当栈里已经有expr opt AND expr的时候,本来应该按照左结合规则直接进行归约,但是bison却必须读到下一个字符才进行归约。
而如果下一个字符是AND,那么就出现了问题:
因为此时首先已有的四个token可以归约为expr,与此同时,AND前还可以归约出一个为空的opt。
然后就出现了问题!(?)
那就是一次归约只能出一个token(就不能归约两次么……),所以出现了归约/归约冲突。

不过这些都是根据output文件推出来的,至于bison为什么会生成这么诡异的规则……emmmmmm……我也不到啊!

但是总而言之,那就是:

在左结合的操作符的左边,不能有可以归约为空的token! 不然会导致归约/归约冲突。
另外,似乎在可以嵌套的括号右侧,也不能有可以归约为空的token(但是我自己还没有测试)

所以如上代码应该改成:

expr:     NUM    | expr opt AND expr    | expr AND expr    ;opt: NOT    ;

(如有错漏,还望指摘)

转载地址:http://ctxzi.baihongyu.com/

你可能感兴趣的文章