private DirectCompilerResult visitPow(DirectCompilerResult left, DirectCompilerResult right) { if (left.getExpression() instanceof NullLiteralExpr || right.getExpression() instanceof NullLiteralExpr) { // optimization: if either left or right is a null literal, just null return DirectCompilerResult.of(new NullLiteralExpr(), BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } else { EnclosedExpr leftCasted = castToBigDecimal(left.getExpression()); EnclosedExpr rightCasted = castToBigDecimal(right.getExpression()); MethodCallExpr powCall = new MethodCallExpr(new NameExpr(CompiledFEELSupport.class.getSimpleName()), "pow"); powCall.addArgument(leftCasted); powCall.addArgument(rightCasted); Expression result = groundToNullIfAnyIsNull(powCall, leftCasted, rightCasted); return DirectCompilerResult.of(result, BuiltInType.NUMBER, DirectCompilerResult.mergeFDs(left, right)); } }
private DirectCompilerResult visitMult(DirectCompilerResult left, DirectCompilerResult right) { if (left.getExpression() instanceof NullLiteralExpr || right.getExpression() instanceof NullLiteralExpr) { // optimization: if either left or right is a null literal, just null return DirectCompilerResult.of(new NullLiteralExpr(), BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } else if (left.resultType == BuiltInType.NUMBER && right.resultType == BuiltInType.NUMBER) { Expression l = castToBigDecimal(left.getExpression()); Expression r = castToBigDecimal(right.getExpression()); MethodCallExpr addCall = new MethodCallExpr(l, "multiply"); addCall.addArgument(r); addCall.addArgument(DECIMAL_128); Expression result = groundToNullIfAnyIsNull(addCall, l, r); return DirectCompilerResult.of(result, BuiltInType.NUMBER, DirectCompilerResult.mergeFDs(left, right)); } else { // fallback support strategy: MethodCallExpr addCall = new MethodCallExpr(null, "mult"); addCall.addArgument(left.getExpression()); addCall.addArgument(right.getExpression()); Expression result = groundToNullIfAnyIsNull(addCall, left.getExpression(), right.getExpression()); return DirectCompilerResult.of(result, BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } }
private DirectCompilerResult visitDiv(DirectCompilerResult left, DirectCompilerResult right) { if (left.getExpression() instanceof NullLiteralExpr || right.getExpression() instanceof NullLiteralExpr) { // optimization: if either left or right is a null literal, just null return DirectCompilerResult.of(new NullLiteralExpr(), BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } else if (left.resultType == BuiltInType.NUMBER && right.resultType == BuiltInType.NUMBER) { // right might be zero, hence if divide-by-zero we should ground to null. MethodCallExpr addCall = new MethodCallExpr(null, "div"); EnclosedExpr l = castToBigDecimal(left.getExpression()); EnclosedExpr r = castToBigDecimal(right.getExpression()); addCall.addArgument(l); addCall.addArgument(r); Expression result = groundToNullIfAnyIsNull(addCall, l, r); return DirectCompilerResult.of(result, BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } else { // fallback support strategy: MethodCallExpr addCall = new MethodCallExpr(null, "div"); addCall.addArgument(left.getExpression()); addCall.addArgument(right.getExpression()); Expression result = groundToNullIfAnyIsNull(addCall, left.getExpression(), right.getExpression()); return DirectCompilerResult.of(result, BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } }
private DirectCompilerResult visitSub( DirectCompilerResult left, DirectCompilerResult right ) { if (left.getExpression() instanceof NullLiteralExpr || right.getExpression() instanceof NullLiteralExpr) { // optimization: if either left or right is a null literal, just null return DirectCompilerResult.of(new NullLiteralExpr(), BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } else if ( left.resultType == BuiltInType.STRING && right.resultType == BuiltInType.STRING ) { // DMN spec Table 45 // Subtraction is undefined. // incosistent when FEEL is in evaluation mode (in contrast to this compilation mode), // for now is more important to check the actual java code produced BinaryExpr postFixMinus = new BinaryExpr(left.getExpression(), new StringLiteralExpr("-"), BinaryExpr.Operator.PLUS); BinaryExpr plusCall = new BinaryExpr(postFixMinus, right.getExpression(), BinaryExpr.Operator.PLUS); Expression result = groundToNullIfAnyIsNull(plusCall, left.getExpression(), right.getExpression()); return DirectCompilerResult.of(result, BuiltInType.STRING, DirectCompilerResult.mergeFDs(left, right)); } else if ( left.resultType == BuiltInType.NUMBER && right.resultType == BuiltInType.NUMBER ) { Expression l = castToBigDecimal(left.getExpression()); Expression r = castToBigDecimal(right.getExpression()); MethodCallExpr subtractCall = new MethodCallExpr(l, "subtract"); subtractCall.addArgument(r); subtractCall.addArgument(DECIMAL_128); Expression result = groundToNullIfAnyIsNull(subtractCall, l, r); return DirectCompilerResult.of(result, BuiltInType.NUMBER, DirectCompilerResult.mergeFDs(left, right)); } else { // fallback support strategy; to avoid the below, will require to match all the possible conbination in InfixOpNode#sub MethodCallExpr addCall = new MethodCallExpr(null, "sub"); addCall.addArgument(left.getExpression()); addCall.addArgument(right.getExpression()); Expression result = groundToNullIfAnyIsNull(addCall, left.getExpression(), right.getExpression()); return DirectCompilerResult.of(result, BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right)); } }
if (left.getExpression() instanceof StringLiteralExpr && right.getExpression() instanceof StringLiteralExpr) { BinaryExpr plusCall = new BinaryExpr(left.getExpression(), right.getExpression(), BinaryExpr.Operator.PLUS); Expression result = groundToNullIfAnyIsNull(plusCall, left.getExpression(), right.getExpression()); return DirectCompilerResult.of(result, BuiltInType.STRING, DirectCompilerResult.mergeFDs(left, right)); } else { addCall.addArgument(r); addCall.addArgument(DECIMAL_128); Expression result = groundToNullIfAnyIsNull(addCall, l, r); return DirectCompilerResult.of(result, BuiltInType.NUMBER, DirectCompilerResult.mergeFDs(left, right)); } else { addCall.addArgument(left.getExpression()); addCall.addArgument(right.getExpression()); Expression result = groundToNullIfAnyIsNull(addCall, left.getExpression(), right.getExpression()); return DirectCompilerResult.of(result, BuiltInType.UNKNOWN, DirectCompilerResult.mergeFDs(left, right));