Bison 野牛:修正了移位/减少错误,不知道怎么做

Bison 野牛:修正了移位/减少错误,不知道怎么做,bison,yacc,shift-reduce-conflict,Bison,Yacc,Shift Reduce Conflict,因此,我的语法发生了可怕的变化/减少了错误。下面是一个最小的测试用例: %token PLUS MINUS TIMES DIVIDE NUMBER %token EQUAL NEQUAL GREATER LESS NOT %left EQUAL NEQUAL %left GREATER LESS %left PLUS MINUS %left TIMES DIVIDE %left UMINUS NOT %% exp : exp bi

因此,我的语法发生了可怕的变化/减少了错误。下面是一个最小的测试用例:

%token PLUS MINUS TIMES DIVIDE NUMBER
%token EQUAL NEQUAL GREATER LESS NOT

%left   EQUAL   NEQUAL
%left   GREATER LESS
%left   PLUS    MINUS
%left   TIMES   DIVIDE
%left   UMINUS  NOT

%%

exp             : exp binop exp
                | unop exp
                | NUMBER
                ;

binop           : MINUS
                | PLUS
                | TIMES
                | DIVIDE
                | EQUAL
                | NEQUAL
                | GREATER
                | LESS
                ;

unop            : MINUS %prec UMINUS
                | NOT
                ;

%%
然而,通过实验,我设法解决了这个问题:

%token PLUS MINUS TIMES DIVIDE NUMBER
%token EQUAL NEQUAL GREATER LESS NOT

%left   EQUAL   NEQUAL
%left   GREATER LESS
%left   PLUS    MINUS
%left   TIMES   DIVIDE
%left   UMINUS  NOT

%%

exp             : binops
                | unops
                | NUMBER
                ;

unops           : MINUS exp %prec UMINUS
                | NOT exp
                ;

binops          : exp MINUS exp
                | exp PLUS exp
                | exp TIMES exp
                | exp DIVIDE exp
                | exp EQUAL exp
                | exp NEQUAL exp
                | exp GREATER exp
                | exp LESS exp
                ;

%%

有人能解释一下为什么我一开始就有移位/减少错误,以及为什么这样做有效吗?这是正确的解决方案吗?如果不是,那是什么?

在您的第一个语法中,优先级声明完全不起作用。优先级仅适用于包含具有优先级的端子的备选方案;在您的第一个语法中,这将是
binop
unop
的产品。但这些产品的替代品是完全明确的;决定将
PLUS
减少到
binop
时不需要优先权

在第二种语法中,优先关系确实会产生影响,因为相互竞争的不明确替代品(为
binops
profos
制作的产品)直接包括终端

换句话说,优先级不会“查看”非终结符