我正在尋找一種相對簡單(與編寫解析器相比)的方式來評估Java中的布爾表達式,並且我不想使用JEP庫。Java中的布爾表達式評估
我有一個字符串表達式,如:(x > 4 || x < 8 && p > 6)
,我的目標是用值替換變量。
有沒有一種方法可以評估這個表達式?
請記住,這可以是任何深度級別,因此編寫解析器將非常複雜。
我正在尋找一種相對簡單(與編寫解析器相比)的方式來評估Java中的布爾表達式,並且我不想使用JEP庫。Java中的布爾表達式評估
我有一個字符串表達式,如:(x > 4 || x < 8 && p > 6)
,我的目標是用值替換變量。
有沒有一種方法可以評估這個表達式?
請記住,這可以是任何深度級別,因此編寫解析器將非常複雜。
JUEL提供了Java的統一表達式語言的實現,而不必明確地綁定到JSP。這是它的Quick Start guide,表達式評估(該頁上的#3)是您感興趣的部分。
或者,Spring 3.0提供了它自己的(儘管有點類似)表達式語言。這個選項只有在你已經使用Spring的時候纔有意義 - 不過我不會爲了EL而使用它。
使用Apache Commons Jexl;這正是爲這樣的要求而設計的。
有可用的API在http://lts.online.fr/dev/java/math.evaluator/
例子:
MathEvaluator m = new MathEvaluator("-5-6/(-2) + sqr(15+x)");
m.addVariable("x", 15.1d);
System.out.println(m.getValue());
這個鏈接似乎沒有工作,至少在撰寫本文時。此外,這個庫是否支持比較運算符和像OP那樣的布爾值? – andr 2012-12-31 11:18:22
這裏是表達評估框架
信息頁面的最新資源在http://expressionoasis.vedantatree.com/
我發現這裏列出的庫太複雜了,無法滿足我的需求。我結束了使用Fscript: http://fscript.sourceforge.net/
使用JEXL(http://commons.apache.org/jexl/),你可以做到這一點像這樣
JexlEngine jexl = new JexlEngine();
jexl.setSilent(true);
jexl.setLenient(true);
Expression expression = jexl.createExpression("(a || b && (c && d))");
JexlContext jexlContext = new MapContext();
//b and c and d should pass
jexlContext.set("b",true);
jexlContext.set("c",true);
jexlContext.set("d",true);
assertTrue((Boolean)expression.evaluate(jexlContext));
jexlContext = new MapContext();
//b and c and NOT d should be false
jexlContext.set("b",true);
jexlContext.set("c",true);
//note this works without setting d to false on the context
//because null evaluates to false
assertFalse((Boolean)expression.evaluate(jexlContext));
我與jexl有一個問題是它的優先級。我有一個需要評估||的案例在評估&&之前。所以上面的表達式變成(a || b)&&(c && d)。在jexl中,使用「a」的上下文將評估爲true。 – Joseph 2012-12-13 19:02:45
僅供參考:我試着用'(a || b)&&(c && d)'表達的例子,它似乎是固定的。只是'一'評估爲'假',這是正確的。 – membersound 2013-01-17 15:26:25
嘗試JANINO http://docs.codehaus.org/display/JANINO/Home 這是非常簡單的使用,如(從http://docs.codehaus.org/display/JANINO/Basic拍攝):
你可以試試這個庫https://github.com/Shy-Ta/expression-evaluator-demo - 閱讀我有很多例子。該庫使用java和groovy。
除了支持這個用例外,它還支持很多其他類似excel的函數。此外,添加新功能非常簡單,如示例中所示。
ExpressionsEvaluator evalExpr = ExpressionsFactory.create("(x > 4 || x < 8 && p > 6)");
Map<String, Object> variables = new HashMap<String, Object>();
variables.put("x", 100);
variables.put("p", 10);
evalExpr.eval();
+1這是一個如何使用它的好例子。 http://commons.apache.org/jexl/reference/examples.html – blak3r 2010-06-17 17:05:21