更改运算符优先级

时间:2011-06-04 22:56:12

标签: algorithm abstract-syntax-tree operator-precedence

更改具体表达式的运算符优先级的最佳方法是什么?

例如我有一个班级:

class A(){ 
   def multiply(a) { 
       ... 
   } 

   def plus(a) { 
       ... 
   } 

   def minus(b) {
       ...
   }

} 

a = new A() 
b = new A() 
c = new A() 

d = a + (b - c) * d

由于乘法的优先级高于+-,因此我得到了表格的AST

  +
 / \
a   *
   / \
  -   d
 / \
b   c

*优先级低于+-的树转换为树的最简单方法是什么?我假设只允许对括号-+进行分组,即表达式(a * b - c) * d无效且不应作为输入。

2 个答案:

答案 0 :(得分:4)

您只需在代码中添加括号即可。这可能会比使用AST转换更容易理解您的代码。

答案 1 :(得分:3)

可以使用AST转换来改变它,但要做到正确是一件很棘手的事情......

如果您将脚本加载到GroovyConsole中,然后打开AST浏览器,您将看到此树的作业:

Binary - ( d = ( a & ( b >> c ) ) )
  Variable - d
  Binary - ( a & ( b >> c ) )
    Variable - a
    Binary - ( b >> c )
      Variable - b
      Variable - c

正如您所看到的,节点是基于默认运算符优先级执行的,并且创建了org.codehaus.groovy.ast.expr.BinaryExpressionorg.codehaus.groovy.ast.expr.VariableExpression AST节点的树。

您需要编写一个AST变换,该变换扫描树中的BinaryExpression节点,然后重新排序这些树,以便按照您自己的operation字段优先级对它们进行排序。

或者,您可以在代码中使用括号,如Don建议: - )