Bison:由于冲突,规则在解析器中无用 [-Wother]

Bison: rule useless in parser due to conflicts [-Wother]

我有这个语法,它应该从 java 代码中生成 java 字节代码。我知道这个警告之前已经在很多问题中得到解决,但我找不到与我的问题类似的问题。 它特别针对这两条规则显示此警告:

statement_list: 
    {
        $<stmt_type>$.next = $<stmt_type>0.next;
    }
     statement 
    | 
    {
        $<stmt_type>$.next = strdup(genLabel().c_str());    //generate label for statement and assign it to statement list next
    }
    statement_list 
    {
        $<stmt_type>$.next = $<stmt_type>0.next;
        fout<<$<stmt_type>1.next<<":"<<endl;    //mark statement with statement list next label
    }
    statement 
    ;

还有这个

b_expression:
expression RELA_OP expression       
    {$$ = $<bexpr_type>0;relaCast(string(),$$.nTrue,$$.nFalse);}
|{/* addding some strings to this action */ } b_expression BOOL_OP b_expression

我需要在解析每个语句以在代码生成中使用它之前用它的 next 标记每个语句。 当我从 statement_list 中删除语义操作时,它的错误消失了,但我没有为 b_expression.

尝试相同的操作

Bison 只向前看 1 个令牌来决定应用哪个生产。 您的两个产品 for 语句都在 解析器已读取任何标记以了解将应用哪个产生式。

如果您直接在 yacc 规则中生成带有标签的类似程序集的堆栈代码,您通常使用如下内容:

if_statement: IF condition {
                      $$ = gen_label();
                      gen_code(JUMP_FALSE, $$); }
              THEN block {
                      $$ = gen_label();
                      gen_code(JUMP, $$);
                      gen_code(LABEL, ); }
              ELSE block {
                      gen_code(LABEL, ); }

while_statement: WHILE { gen_code(LABEL, $$ = gen_label()); }
                 condition { gen_code(JUMP_FALSE, $$ = gen_label); }
                 block { gen_code(JUMP, ); gen_code(LABEL, ); }

如果您直接生成字节码,则没有 'labels' 这样的 -- 当您生成前向分支时,您会记住字节码中目标偏移量应该到达的位置以及何时到达输出标签的位置,回溯分支以跳转到当前位置。