我试图写一个Java例程来计算数学表达式从字符串值,如:
"5 + 3" "10-4 * 5" "(1 + 10) * 3"
我想避免很多如果-then-else语句。 我该怎么做呢?
我试图写一个Java例程来计算数学表达式从字符串值,如:
"5 + 3" "10-4 * 5" "(1 + 10) * 3"
我想避免很多如果-then-else语句。 我该怎么做呢?
当前回答
你可以看看Symja框架:
ExprEvaluator util = new ExprEvaluator();
IExpr result = util.evaluate("10-40");
System.out.println(result.toString()); // -> "-30"
请注意,可以计算更复杂的表达式:
// D(...) gives the derivative of the function Sin(x)*Cos(x)
IAST function = D(Times(Sin(x), Cos(x)), x);
IExpr result = util.evaluate(function);
// print: Cos(x)^2-Sin(x)^2
其他回答
你可以看看Symja框架:
ExprEvaluator util = new ExprEvaluator();
IExpr result = util.evaluate("10-40");
System.out.println(result.toString()); // -> "-30"
请注意,可以计算更复杂的表达式:
// D(...) gives the derivative of the function Sin(x)*Cos(x)
IAST function = D(Times(Sin(x), Cos(x)), x);
IExpr result = util.evaluate(function);
// print: Cos(x)^2-Sin(x)^2
这是另一个有趣的选择 https://github.com/Shy-Ta/expression-evaluator-demo
它的用法非常简单,可以完成工作,例如:
ExpressionsEvaluator evalExpr = ExpressionsFactory.create("2+3*4-6/2");
assertEquals(BigDecimal.valueOf(11), evalExpr.eval());
在我的大学项目中,我正在寻找一个既支持基本公式又支持更复杂方程(特别是迭代运算符)的解析器/求值器。我发现了一个非常好的JAVA和。net开源库,叫做mXparser。我将给出几个例子,让大家对语法有一些感觉,如需进一步指导,请访问项目网站(特别是教程部分)。
https://mathparser.org/
https://mathparser.org/mxparser-tutorial/
https://mathparser.org/api/
举几个例子
一个简单的开始
Expression e = new Expression("( 2 + 3/4 + sin(pi) )/2");
double v = e.calculate()
2 -用户定义的参数和常量
Argument x = new Argument("x = 10");
Constant a = new Constant("a = pi^2");
Expression e = new Expression("cos(a*x)", x, a);
double v = e.calculate()
3 -用户定义的函数
Function f = new Function("f(x, y, z) = sin(x) + cos(y*z)");
Expression e = new Expression("f(3,2,5)", f);
double v = e.calculate()
4 -迭代
Expression e = new Expression("sum( i, 1, 100, sin(i) )");
double v = e.calculate()
最近发现的-如果你想尝试语法(并查看高级用例),你可以下载由mXparser支持的标量计算器应用程序。
如果我们要实现它,那么我们可以使用下面的算法
While there are still tokens to be read in, 1.1 Get the next token. 1.2 If the token is: 1.2.1 A number: push it onto the value stack. 1.2.2 A variable: get its value, and push onto the value stack. 1.2.3 A left parenthesis: push it onto the operator stack. 1.2.4 A right parenthesis: 1 While the thing on top of the operator stack is not a left parenthesis, 1 Pop the operator from the operator stack. 2 Pop the value stack twice, getting two operands. 3 Apply the operator to the operands, in the correct order. 4 Push the result onto the value stack. 2 Pop the left parenthesis from the operator stack, and discard it. 1.2.5 An operator (call it thisOp): 1 While the operator stack is not empty, and the top thing on the operator stack has the same or greater precedence as thisOp, 1 Pop the operator from the operator stack. 2 Pop the value stack twice, getting two operands. 3 Apply the operator to the operands, in the correct order. 4 Push the result onto the value stack. 2 Push thisOp onto the operator stack. While the operator stack is not empty, 1 Pop the operator from the operator stack. 2 Pop the value stack twice, getting two operands. 3 Apply the operator to the operands, in the correct order. 4 Push the result onto the value stack. At this point the operator stack should be empty, and the value stack should have only one value in it, which is the final result.
看来应该由JEP来做这项工作