虽然规则匹配,但在匹配语法时令牌为空

时间:2014-01-09 09:54:56

标签: antlr4

所以我的规则是

/* Addition and subtraction have the lowest precedence. */
additionExp returns [double value]
    :    m1=multiplyExp       {$value = $m1.value;} 
         ( op=AddOp m2=multiplyExp )* {
                                       if($op != null){ // test if matched
                                         if($op.text == "+" ){
                                           $value += $m2.value;
                                         }else{
                                           $value -= $m2.value;
                                         }                                         
                                        }
                                       }
    ;

AddOp : '+' | '-' ;

我的测试是3 + 4,但是op.text总是返回NULL而不是char。

有谁知道我如何测试AddOp的值?

ANTLR4 Actions and Attributes的示例中,它应该有效:

stat: ID '=' INT ';'
   {
    if ( !$block::symbols.contains($ID.text) ) {
      System.err.println("undefined variable: "+$ID.text);
    }
   }
   | block
   ;

1 个答案:

答案 0 :(得分:1)

您确定$op.text始终是null吗?您的比较似乎是检查$op.text=="+"而不是检查null

  1. 我总是提出这些答案时建议您在使用ANTLR 4时将所有操作代码迁移到侦听器和/或访问者。它将清理您的语法并大大简化代码的长期维护。

  2. 这可能是此处的主要问题:比较Java中的String对象应使用equals"+".equals($op.text)执行。请注意,即使NullPointerException$op.text,我也使用此排序来保证您永远不会获得null

  3. 我建议删除op=标签并改为引用$AddOp

    1. 当您切换到使用侦听器和访问者时,删除显式标签会略微减小解析树的大小。

    2. (仅与高级用户相关)在涉及语法错误的某些边缘情况下,如果对象仍存在于解析树中,则可能无法分配标签。特别是,当标签分配给规则引用(您的op标签已分配给令牌引用)时,可能会发生这种情况,并且标记的规则中会出现错误。如果您通过侦听器/访问者中自动生成的方法引用上下文对象,即使未分配标签,实例也将可用,从而提高报告某些错误详细信息的能力。