首页
学习
活动
专区
圈层
工具
发布

Mvel评估
EN

Stack Overflow用户
提问于 2014-06-16 19:50:39
回答 2查看 9.6K关注 0票数 3

问题陈述:假设我有一个表达式(a + b + c),我想计算它的值并赋值给某个变量。稍后,我想在其他逻辑中使用该变量值。这一切都是通过MVEL完成的。问题是,如果(a,b,c)之外的任何人都是null,则MVEL将以字符串格式进行计算。

因此,为了避免这种情况,我创建了自己的函数来传递每个对象,如果为null,则将其设为零。

下面是示例代码

代码语言:javascript
复制
public class MvelTest {

    public static void main(String[] args) {

        Map map = new HashMap();

        VariableResolverFactory functionFactory = new MapVariableResolverFactory(map);
        MVEL.eval("checkNullValue = def (x) { x == null ? 0 : x };", functionFactory);

        map.put("a", null);
        map.put("b", 1);
        map.put("c", 1);

        Serializable str = MVEL.compileExpression("( ( checkNullValue(a) + checkNullValue(b) + checkNullValue(c) ) > 2 ) ? d=2 : d=3");

        MVEL.executeExpression(str, map, functionFactory);
        System.out.println(map);
        System.out.println(map.get("d"));
    }
}

输出

代码语言:javascript
复制
{checkNullValue=function_prototype:null, b=1, c=1, a=null}
null

我不能在这里获得"d"的值,如果我删除工厂和空检查函数,它就会运行,我能够获得"d"的值。但是我必须使它对于算术运算为空安全,因为MVEL不能处理这一点。

同样,MVEL以false的形式返回(null * 23)

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2014-06-17 13:44:41

问题得到了解决,我实际上是在为VariableResolverFactory创建静态引用,并在每次求值时引用相同的引用,每次执行时我都将其更改为新实例,并且它起作用了。

代码语言:javascript
复制
 public VariableResolverFactory getMvelFactory(Map contextMap) {
        VariableResolverFactory functionFactory = new MapVariableResolverFactory(contextMap);
        MVEL.eval("checkNullValue = def (x) { x == null ? 0 : x };", functionFactory);

        return functionFactory;
    }
票数 0
EN

Stack Overflow用户

发布于 2014-06-16 22:16:14

问题出在你的三元运算符。我不确定MVEL如何计算这些(在Java中使用它们的方式是非法的),但似乎将赋值放在then/else部分不起作用……或者更确切地说,它(无论出于什么原因)对“then”部分(在:之前)有效,但对“else”部分(在:之后)无效。

所以,如果和是空的,那么不管你是否在使用> 2 -check函数,它都可以工作,否则它就失败了。

你应该修正你的表达式,把赋值放在三元运算符的前面:

代码语言:javascript
复制
MVEL.compileExpression("d = cnv(a) + cnv(b) + cnv(c) > 2 ? 2 : 3")

更新:一般来说,这是我观察到的,独立于abccnv

代码语言:javascript
复制
MVEL.compileExpression("true  ? d=1 : d=2"); // d ends up as 1
MVEL.compileExpression("false ? d=1 : d=2"); // d is null / unknown
MVEL.compileExpression("d = guard ? 1 : 2"); // always works
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/24243055

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档