killme2008/aviatorscript

自定义round方法, 现在使用遇到if词法解析问题

eric521237 opened this issue · 4 comments

@test
public void getFunTest03(){
Map<String, Object> p = new HashMap<>();
p.put("ycly_a", 2);
p.put("sxcn_ydccl", 3);
p.put("sxcn_jjgzzey", 4);
p.put("mbcn_ydccl", 2);
p.put("mbcn_jjgzzey", 5);
p.put("qwcn_ydccl", 7);
p.put("bdcn_ydccl", 1);
p.put("qwcn_ndccl", 8);
p.put("qwcn_jjgzzey", 11);
p.put("bdcn_jjgzzey", 6);

    Object execute = executor.execute("round ( if ( ycly_a >= sxcn_ydccl ) { sxcn_jjgzzey } elsif ( ycly_a >= mbcn_ydccl && ycly_a < sxcn_ydccl ) { ( mbcn_jjgzzey * ( ( ycly_a / mbcn_ydccl -1 ) *0.8 +1 ) ) } elsif ( ycly_a >= qwcn_ydccl && ycly_a < mbcn_ydccl ) { ( mbcn_jjgzzey / ( ( mbcn_ydccl / ycly_a -1 ) *0.7 +1 ) ) } elsif ( ycly_a >= bdcn_ydccl && ycly_a < qwcn_ndccl ) { ( qwcn_jjgzzey / ( ( qwcn_ydccl / ycly_a -1 ) *0.65 +1 ) ) } elsif ( ycly_a < bdcn_ydccl ) { bdcn_jjgzzey } else {0 } ,0 )", p);

    System.out.println(execute);
}

com.googlecode.aviator.exception.ExpressionSyntaxErrorException: Syntax error: The function name if is a reserved keyword at 11, lineNumber: 1, token : [type='Char',lexeme='(',index=11],
while parsing expression: round ( if (^^^

at com.googlecode.aviator.AviatorEvaluatorInstance.validate(AviatorEvaluatorInstance.java:1587)

@component("round")
public class MathRoundFunc extends MathRoundFunction {

@Override
public String getName() {
    return "round";
}

@Override
public AviatorObject call(Map<String, Object> env, AviatorObject arg1, AviatorObject arg2) {
    Number val = FunctionUtils.getNumberValue(arg1, env);
    Number precision = FunctionUtils.getNumberValue(arg2, env);
    if(val == null) {
        throw new NullPointerException("round: arg is null");
    }
    if(precision == null) {
        throw new NullPointerException("round: precision is null");
    }
    BigDecimal bigDecimal = new BigDecimal(val.toString());
    bigDecimal = bigDecimal.setScale(precision.intValue(), BigDecimal.ROUND_HALF_UP);
    return FunctionUtils.wrapReturn(bigDecimal);
}

}

使用math.round 和if 一起使用也会有问题

static {
reserveKeyword(Variable.TRUE);
reserveKeyword(Variable.FALSE);
reserveKeyword(Variable.NIL);
reserveKeyword(Variable.LAMBDA);
reserveKeyword(Variable.FN);
reserveKeyword(Variable.END);
reserveKeyword(Variable.IF);
reserveKeyword(Variable.ELSE);
reserveKeyword(Variable.FOR);
reserveKeyword(Variable.IN);
reserveKeyword(Variable.RETURN);
reserveKeyword(Variable.BREAK);
reserveKeyword(Variable.CONTINUE);
reserveKeyword(Variable.LET);
reserveKeyword(Variable.WHILE);
reserveKeyword(Variable.ELSIF);
reserveKeyword(Variable.TRY);
reserveKeyword(Variable.CATCH);
reserveKeyword(Variable.FINALLY);
reserveKeyword(Variable.THROW);
reserveKeyword(Variable.NEW);
reserveKeyword(Variable.USE);
}

public static boolean isReservedKeyword(final String name) {
return RESERVED.containsKey(name);
}

这个地方验证关键字是?

函数的参数目前并不支持语句,所以你可以先赋值一个变量来调用:

let a = if(true} {
  1
} else {
  2
};

round(a)

函数的参数目前并不支持语句,所以你可以先赋值一个变量来调用:

let a = if(true} {
  1
} else {
  2
};

round(a)

谢谢回复~