How to resolve a shift/reduce conflict forcing a shift or a reduce?

别等时光非礼了梦想. 提交于 2019-12-06 01:08:39

As far as I can tell, it is not possible to direct the parser to resolve a S/R conflict by choosing to reduce. Though I might be wrong, it is probably ill-advised to proceed this way anyway. Therefore, the only possibilities are either rewriting the grammar, or solving the conflict by shifting.

The following usage of right predecence for THEN and ELSE describes the desired behavior for the if-then-else statement (that is, associating else with the innermost if statement).

%token IF THEN ELSE variable
%right THEN ELSE

%%

stmt
    : expr
    | if_stmt
    ;

if_stmt
    : IF expr THEN stmt
    | IF expr THEN stmt ELSE stmt
    ;

expr
    : variable
    ;

By choosing right association for the above tokens, the following sequence:

IF expr1 THEN IF expr2 THEN IF expr3 THEN x ELSE y

is parsed as:

IF expr1 THEN (IF expr2 THEN (IF expr3 THEN (x ELSE (y))))

and Bison does not complain about the case any longer.

Remember that you can always run bison file.y -r all and inspect file.output in order to see if the generated parser state machine is correct.

Well, the default resolution for a shift/reduce conflict is to shift, so if that's what you want, you don't need to do anything (other than ignoring the warning).

If you want to resolve a shift/reduce conflict by reducing, you can use the precedence rules -- just make sure that the rule to be reduced is higher precedence than the token to be shifted. The tricky part comes if there are multiple shift/reduce conflicts involving the same rules and tokens, it may not be possible to find a globally consistent set of precedences for the rules and tokens which resolves things the way you want.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!