JAVA - 表达式解析&评估图书馆

时间:2012-08-14 07:21:01

标签: java expression

我正在寻找一个JAVA库来解析&评估表达。我搜索并尝试了一些像Apache的JEXL和Jeval这样的库,但它们并不是我需要的。

我的要求:

  1. 支持所有值类型(即int,double,boolean,String等)
  2. 支持所有已知的数学和数学逻辑运算符(+, - ,*,<,< =等)
  3. 支持变量(没有任何特殊符号 - 例如在Jeval变量中应该写成#{a} - 对我来说不够好)
  4. 支持自定义功能 - 具有类型强制和验证功能
  5. 有什么建议吗?

4 个答案:

答案 0 :(得分:6)

试试Janino。它是一个运行时内存编译器,可用作表达式求值程序。也许这对你来说是对的。

答案 1 :(得分:3)

与建议一样,您可以使用JavaScript。但是你也可以看看Spring EL,它支持你的要求。

答案 2 :(得分:2)

您可以尝试mXparser - 它支持您的大部分要求:

  1. 它基于double,因此支持int,另外支持布尔值,因为true = 1且false = 0.不幸的是不支持字符串。
  2. 布尔示例:

    import org.mariuszgromada.math.mxparser.*;
    ...
    ...
    Constant T = new Constant("T = 1");
    Constant F = new Constant("F = 0");
    Expression e = new Expression("T && (F || (F && T))", T, F);
    System.out.println(e.getExpressionString() + " = " + e.calculate());
    

    结果:

    T && (F || (F && T)) = 0.0
    
    1. mXparser 广泛支持运营商,功能等。请检查mXparser math collection。有什么好处,您可以在库中使用帮助功能。
    2. 示例:

      import org.mariuszgromada.math.mxparser.*;
      ...
      ...
      mXparser.consolePrintHelp("operator");
      

      结果:

      Help content: 
      
          2. +                   <Operator>              addition
          3. -                   <Operator>              subtraction
          4. *                   <Operator>              multiplication
          5. /                   <Operator>              division
          6. ^                   <Operator>              exponentiation
          7. !                   <Operator>              factorial
          8. #                   <Operator>              modulo function
          9. &                   <Boolean Operator>      logical conjunction (AND)
         10. &&                  <Boolean Operator>      logical conjunction (AND)
         11. /\                  <Boolean Operator>      logical conjunction (AND)
         12. ~&                  <Boolean Operator>      NAND - Sheffer stroke
         13. ~&&                 <Boolean Operator>      NAND - Sheffer stroke
         14. ~/\                 <Boolean Operator>      NAND - Sheffer stroke
         15. |                   <Boolean Operator>      logical disjunction (OR)
         16. ||                  <Boolean Operator>      logical disjunction (OR)
         17. \/                  <Boolean Operator>      logical disjunction (OR)
         18. ~|                  <Boolean Operator>      logical NOR
         19. ~||                 <Boolean Operator>      logical NOR
         20. ~\/                 <Boolean Operator>      logical NOR
         21. (+)                 <Boolean Operator>      exclusive or (XOR)
         22. -->                 <Boolean Operator>      implication (IMP)
         23. <--                 <Boolean Operator>      converse implication (CIMP)
         24. -/>                 <Boolean Operator>      material nonimplication (NIMP)
         25. </-                 <Boolean Operator>      converse nonimplication (CNIMP)
         26. <->                 <Boolean Operator>      logical biconditional (EQV)
         27. ~                   <Boolean Operator>      negation
         28. ¬                   <Boolean Operator>      negation
        162. add                 <Variadic Function>     (2.4) Summation operator add(a1,a2,a3,...,an)
        168. sum                 <Calculus Operator>     summation operator (SIGMA) sum(i, from, to, f(i,...))
        169. prod                <Calculus Operator>     product operator (PI) prod(i, from, to, f(i,...))
        170. int                 <Calculus Operator>     definite integral operator ( int(f(x,...), x, a, b) )
        171. der                 <Calculus Operator>     derivative operator ( der(f(x,...), x) ) 
        172. der-                <Calculus Operator>     left derivative operator ( der-(f(x,...), x) ) 
        173. der+                <Calculus Operator>     right derivative operator ( der+(f(x,...), x) ) 
        174. dern                <Calculus Operator>     n-th derivative operator ( dern(f(x,...), x) ) 
        175. diff                <Calculus Operator>     forward difference operator
        176. difb                <Calculus Operator>     backward difference operator
        177. avg                 <Calculus Operator>     (2.4) Average operator avg(i, from, to, f(i,...))
        178. vari                <Calculus Operator>     (2.4) Bias-corrected sample variance operator vari(i, from, to, f(i,...))
        179. stdi                <Calculus Operator>     (2.4) Bias-corrected sample standard deviation operator stdi(i, from, to, f(i,...))
        180. mini                <Calculus Operator>     (2.4) Minimum value mini(i, from, to, f(i,...))
        181. maxi                <Calculus Operator>     (2.4) Maximum value maxi(i, from, to, f(i,...))
        182. solve               <Calculus Operator>     (4.0) f(x) = 0 equation solving, function root finding: solve( f(x,...), x, a, b )
        301. @~                  <Bitwise Operator>      (4.0) Bitwise unary complement
        302. @&                  <Bitwise Operator>      (4.0) Bitwise AND
        303. @^                  <Bitwise Operator>      (4.0) Bitwise exclusive OR
        304. @|                  <Bitwise Operator>      (4.0) Bitwise inclusive OR
        305. @<<                 <Bitwise Operator>      (4.0) Signed left shift
        306. @>>                 <Bitwise Operator>      (4.0) Signed right shift
      
      1. 用户定义的变量用户定义的常量是在没有任何特殊形式的情况下创建的。
      2. 示例:

        import org.mariuszgromada.math.mxparser.*;
        ...
        ...
        Argument x = new Argument("x = 10");
        Constant y = new Constant("y = 2");
        Expression e = new Expression("x/y", x, y);
        System.out.println(e.getExpressionString() + " = " + e.calculate());
        

        结果:

        x/y = 5.0
        

        此外,请检查:a)Tutorial - User defined arguments,b)Tutorial - User defined constants

          完全支持
        1. 用户定义的功能
        2. 示例1 - 在运行时定义的主体:

          import org.mariuszgromada.math.mxparser.*;
          ...
          ...
          Function f = new Function("f(x,y) = x*y");
          Expression e = new Expression("20-f(2,5)",f);
          System.out.println(e.getExpressionString() + " = " + e.calculate());
          

          结果1

          20-f(2,5) = 10.0
          

          示例2 - 通过您自己的实现扩展了主体:

          import org.mariuszgromada.math.mxparser.*;
          ...
          ...
          /*
           * Implementing FunctionExtension interface
           */
          public class Addition implements FunctionExtension {
             double x;
             double y;
             public Addition() {
                x = Double.NaN;
                y = Double.NaN;
             }
             public Addition(double x, double y) {
                this.x = x;
                this.y = y;
             }
             public int getParametersNumber() {
                return 2;
             }
             public void setParameterValue(int argumentIndex, double argumentValue) {
                if (argumentIndex == 0) x = argumentValue;
                if (argumentIndex == 1) y = argumentValue;
             }
             public double calculate(double... params) {
                return x+y;
             }
             public FunctionExtension clone() {
                return new Addition(x, y);
             }   
          }
          
          /*
          * Creating extended function
          */
          Function f = new Function("f", new Addition());
          mXparser.consolePrintln("f.calculate(1,2) = " + f.calculate(1,2) );
          /*
          * Using extended function in expression
          */
          Expression e = new Expression("f(2,3)", f);
          System.out.println(e.getExpressionString() + " = " + e.calculate() );
          

          结果2:

          f.calculate(1,2) = 3.0
          f(2,3) = 5.0
          

          此外值得关注整个 mXparser Tutorial

          祝你好运

答案 3 :(得分:0)

如果您没有找到实际的Java表达式评估库,可以选择以下几种解决方案:

  • 使用XPath评估您的表达式。
    • 优点:XPath了解逻辑运算符,您可以使用Xalan的扩展
    • 实现变量和自定义函数
    • 缺点:XPath的类型少于Java
  • 使用JavaScript评估您的表达式。
    • 优点:Javascript非常灵活,当您的要求收紧时仍然适用。您也可以使用Javascript实现变量和自定义函数
    • 缺点:Javascript的类型少于Java
  • 使用JSP的表达式语言(例如使用JUEL
  • 评估您的表达式