org.apache.commons.jexl3
Class JexlArithmetic

java.lang.Object
  extended by org.apache.commons.jexl3.JexlArithmetic

public class JexlArithmetic
extends Object

Perform arithmetic, implements JexlOperator methods.

This is the class to derive to implement new operator behaviors.

The 5 base arithmetic operators (+, - , *, /, %) follow the same evaluation rules regarding their arguments.

  1. If both are null, result is 0
  2. If either is a BigDecimal, coerce both to BigDecimal and perform operation
  3. If either is a floating point number, coerce both to Double and perform operation
  4. Else treat as BigInteger, perform operation and attempt to narrow result:
    1. if both arguments can be narrowed to Integer, narrow result to Integer
    2. if both arguments can be narrowed to Long, narrow result to Long
    3. Else return result as BigInteger
Note that the only exception thrown by JexlArithmetic is and must be ArithmeticException.

Since:
2.0
See Also:
JexlOperator

Nested Class Summary
static interface JexlArithmetic.ArrayBuilder
          Helper interface used when creating an array literal.
static interface JexlArithmetic.MapBuilder
          Helper interface used when creating a map literal.
static class JexlArithmetic.NullOperand
          Marker class for null operand exceptions.
static interface JexlArithmetic.SetBuilder
          Helper interface used when creating a set literal.
static interface JexlArithmetic.Uberspect
          The interface that uberspects JexlArithmetic classes.
 
Field Summary
protected static BigDecimal BIGD_DOUBLE_MAX_VALUE
          Double.MAX_VALUE as BigDecimal.
protected static BigDecimal BIGD_DOUBLE_MIN_VALUE
          Double.MIN_VALUE as BigDecimal.
protected static int BIGD_SCALE
          Default BigDecimal scale.
protected static BigInteger BIGI_LONG_MAX_VALUE
          Long.MAX_VALUE as BigInteger.
protected static BigInteger BIGI_LONG_MIN_VALUE
          Long.MIN_VALUE as BigInteger.
static Pattern FLOAT_PATTERN
          The float regular expression pattern.
 
Constructor Summary
JexlArithmetic(boolean astrict)
          Creates a JexlArithmetic.
JexlArithmetic(boolean astrict, MathContext bigdContext, int bigdScale)
          Creates a JexlArithmetic.
 
Method Summary
 Object add(Object left, Object right)
          Add two values together.
 Object and(Object left, Object right)
          Performs a bitwise and.
 JexlArithmetic.ArrayBuilder arrayBuilder(int size)
          Called by the interpreter when evaluating a literal array.
 Object bitwiseAnd(Object lhs, Object rhs)
          Deprecated.  
 Object bitwiseOr(Object lhs, Object rhs)
          Deprecated.  
 Object bitwiseXor(Object lhs, Object rhs)
          Deprecated.  
protected  int compare(Object left, Object right, String operator)
          Performs a comparison.
 Object complement(Object val)
          Performs a bitwise complement.
 Boolean contains(Object container, Object value)
          Test if left contains right (right matches/in left).
protected  Object controlNullNullOperands()
          The result of +,/,-,*,% when both operands are null.
protected  void controlNullOperand()
          Throw a NPE if arithmetic is strict.
 Iterable<?> createRange(Object from, Object to)
          Creates a literal range.
protected  JexlArithmetic createWithOptions(boolean astrict, MathContext bigdContext, int bigdScale)
          Creates a JexlArithmetic instance.
 Object divide(Object left, Object right)
          Divide the left value by the right.
 Boolean endsWith(Object left, Object right)
          Test if left ends with right.
 boolean equals(Object left, Object right)
          Test if left and right are equal.
 MathContext getMathContext()
          The MathContext instance used for +,-,/,*,% operations on big decimals.
 int getMathScale()
          The BigDecimal scale used for comparison and coericion operations.
 boolean greaterThan(Object left, Object right)
          Test if left > right.
 boolean greaterThanOrEqual(Object left, Object right)
          Test if left >= right.
 Boolean isEmpty(Object object)
          Check for emptyness of various types: Number, Collection, Array, Map, String.
protected  boolean isFloatingPoint(Object o)
          Is Object a floating point number.
protected  boolean isFloatingPointNumber(Object val)
          Test if the passed value is a floating point number, i.e.
protected  boolean isNumberable(Object o)
          Is Object a whole number.
 boolean isStrict()
          Checks whether this JexlArithmetic instance strictly considers null as an error when used as operand unexpectedly.
 boolean lessThan(Object left, Object right)
          Test if left < right.
 boolean lessThanOrEqual(Object left, Object right)
          Test if left <= right.
 Object logicalNot(Object arg)
          Deprecated.  
 JexlArithmetic.MapBuilder mapBuilder(int size)
          Called by the interpreter when evaluating a literal map.
 Object matches(Object lhs, Object rhs)
          Deprecated.  
 Object mod(Object left, Object right)
          left value modulo right.
 Object multiply(Object left, Object right)
          Multiply the left value by the right.
 Number narrow(Number original)
          Given a Number, return back the value using the smallest type the result will fit into.
protected  boolean narrowAccept(Class<?> narrow, Class<?> source)
          Whether we consider the narrow class as a potential candidate for narrowing the source.
 boolean narrowArguments(Object[] args)
          Replace all numbers in an arguments array with the smallest type that will fit.
protected  Number narrowBigDecimal(Object lhs, Object rhs, BigDecimal bigd)
          Given a BigDecimal, attempt to narrow it to an Integer or Long if it fits if one of the arguments is a numberable.
protected  Number narrowBigInteger(Object lhs, Object rhs, BigInteger bigi)
          Given a BigInteger, narrow it to an Integer or Long if it fits and the arguments class allow it.
 Number narrowNumber(Number original, Class<?> narrow)
          Given a Number, return back the value attempting to narrow it to a target class.
 Object negate(Object val)
          Negates a value (unary minus for numbers).
 Object not(Object val)
          Performs a logical not.
 JexlArithmetic options(JexlContext context)
          Apply options to this arithmetic which eventually may create another instance.
 JexlArithmetic options(JexlEngine.Options options)
          Apply options to this arithmetic which eventually may create another instance.
 Object or(Object left, Object right)
          Performs a bitwise or.
protected  BigDecimal roundBigDecimal(BigDecimal number)
          Ensure a big decimal is rounded by this arithmetic scale and rounding mode.
 JexlArithmetic.SetBuilder setBuilder(int size)
          Called by the interpreter when evaluating a literal set.
 Integer size(Object object)
          Calculate the size of various types: Collection, Array, Map, String.
 Boolean startsWith(Object left, Object right)
          Test if left starts with right.
 Object subtract(Object left, Object right)
          Subtract the right value from the left.
 BigDecimal toBigDecimal(Object val)
          Coerce to a BigDecimal.
 BigInteger toBigInteger(Object val)
          Coerce to a BigInteger.
 boolean toBoolean(Object val)
          Coerce to a primitive boolean.
 double toDouble(Object val)
          Coerce to a primitive double.
 int toInteger(Object val)
          Coerce to a primitive int.
 long toLong(Object val)
          Coerce to a primitive long.
 String toString(Object val)
          Coerce to a string.
 Object xor(Object left, Object right)
          Performs a bitwise xor.
 
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
 

Field Detail

BIGD_DOUBLE_MAX_VALUE

protected static final BigDecimal BIGD_DOUBLE_MAX_VALUE
Double.MAX_VALUE as BigDecimal.


BIGD_DOUBLE_MIN_VALUE

protected static final BigDecimal BIGD_DOUBLE_MIN_VALUE
Double.MIN_VALUE as BigDecimal.


BIGI_LONG_MAX_VALUE

protected static final BigInteger BIGI_LONG_MAX_VALUE
Long.MAX_VALUE as BigInteger.


BIGI_LONG_MIN_VALUE

protected static final BigInteger BIGI_LONG_MIN_VALUE
Long.MIN_VALUE as BigInteger.


BIGD_SCALE

protected static final int BIGD_SCALE
Default BigDecimal scale.

See Also:
Constant Field Values

FLOAT_PATTERN

public static final Pattern FLOAT_PATTERN
The float regular expression pattern.

The decimal and exponent parts are optional and captured allowing to determine if the number is a real by checking whether one of these 2 capturing groups is not empty.

Constructor Detail

JexlArithmetic

public JexlArithmetic(boolean astrict)
Creates a JexlArithmetic.

Parameters:
astrict - whether this arithmetic is strict or lenient

JexlArithmetic

public JexlArithmetic(boolean astrict,
                      MathContext bigdContext,
                      int bigdScale)
Creates a JexlArithmetic.

Parameters:
astrict - whether this arithmetic is lenient or strict
bigdContext - the math context instance to use for +,-,/,*,% operations on big decimals.
bigdScale - the scale used for big decimals.
Method Detail

options

public JexlArithmetic options(JexlEngine.Options options)
Apply options to this arithmetic which eventually may create another instance.

Parameters:
options - the JexlEngine.Options to use
Returns:
an arithmetic with those options set
See Also:
createWithOptions(boolean, java.math.MathContext, int)

options

public JexlArithmetic options(JexlContext context)
Apply options to this arithmetic which eventually may create another instance.

Parameters:
context - the context that may extend JexlEngine.Options to use
Returns:
a new arithmetic instance or this
Since:
3.1
See Also:
createWithOptions(boolean, java.math.MathContext, int)

createWithOptions

protected JexlArithmetic createWithOptions(boolean astrict,
                                           MathContext bigdContext,
                                           int bigdScale)
Creates a JexlArithmetic instance. Called by options(...) method when another instance of the same class of arithmetic is required.

Parameters:
astrict - whether this arithmetic is lenient or strict
bigdContext - the math context instance to use for +,-,/,*,% operations on big decimals.
bigdScale - the scale used for big decimals.
Returns:
default is a new JexlArithmetic instance
Since:
3.1
See Also:
options(org.apache.commons.jexl3.JexlEngine.Options)

arrayBuilder

public JexlArithmetic.ArrayBuilder arrayBuilder(int size)
Called by the interpreter when evaluating a literal array.

Parameters:
size - the number of elements in the array
Returns:
the array builder

setBuilder

public JexlArithmetic.SetBuilder setBuilder(int size)
Called by the interpreter when evaluating a literal set.

Parameters:
size - the number of elements in the set
Returns:
the array builder

mapBuilder

public JexlArithmetic.MapBuilder mapBuilder(int size)
Called by the interpreter when evaluating a literal map.

Parameters:
size - the number of elements in the map
Returns:
the map builder

createRange

public Iterable<?> createRange(Object from,
                               Object to)
                        throws ArithmeticException
Creates a literal range.

The default implementation only accepts integers and longs.

Parameters:
from - the included lower bound value (null if none)
to - the included upper bound value (null if none)
Returns:
the range as an iterable
Throws:
ArithmeticException - as an option if creation fails

isStrict

public boolean isStrict()
Checks whether this JexlArithmetic instance strictly considers null as an error when used as operand unexpectedly.

Returns:
true if strict, false if lenient

getMathContext

public MathContext getMathContext()
The MathContext instance used for +,-,/,*,% operations on big decimals.

Returns:
the math context

getMathScale

public int getMathScale()
The BigDecimal scale used for comparison and coericion operations.

Returns:
the scale

roundBigDecimal

protected BigDecimal roundBigDecimal(BigDecimal number)
Ensure a big decimal is rounded by this arithmetic scale and rounding mode.

Parameters:
number - the big decimal to round
Returns:
the rounded big decimal

controlNullNullOperands

protected Object controlNullNullOperands()
The result of +,/,-,*,% when both operands are null.

Returns:
Integer(0) if lenient
Throws:
ArithmeticException - if strict

controlNullOperand

protected void controlNullOperand()
Throw a NPE if arithmetic is strict.

Throws:
ArithmeticException - if strict

isFloatingPointNumber

protected boolean isFloatingPointNumber(Object val)
Test if the passed value is a floating point number, i.e. a float, double or string with ( "." | "E" | "e").

Parameters:
val - the object to be tested
Returns:
true if it is, false otherwise.

isFloatingPoint

protected boolean isFloatingPoint(Object o)
Is Object a floating point number.

Parameters:
o - Object to be analyzed.
Returns:
true if it is a Float or a Double.

isNumberable

protected boolean isNumberable(Object o)
Is Object a whole number.

Parameters:
o - Object to be analyzed.
Returns:
true if Integer, Long, Byte, Short or Character.

narrow

public Number narrow(Number original)
Given a Number, return back the value using the smallest type the result will fit into.

This works hand in hand with parameter 'widening' in java method calls, e.g. a call to substring(int,int) with an int and a long will fail, but a call to substring(int,int) with an int and a short will succeed.

Parameters:
original - the original number.
Returns:
a value of the smallest type the original number will fit into.

narrowAccept

protected boolean narrowAccept(Class<?> narrow,
                               Class<?> source)
Whether we consider the narrow class as a potential candidate for narrowing the source.

Parameters:
narrow - the target narrow class
source - the orginal source class
Returns:
true if attempt to narrow source to target is accepted

narrowNumber

public Number narrowNumber(Number original,
                           Class<?> narrow)
Given a Number, return back the value attempting to narrow it to a target class.

Parameters:
original - the original number
narrow - the attempted target class
Returns:
the narrowed number or the source if no narrowing was possible

narrowBigInteger

protected Number narrowBigInteger(Object lhs,
                                  Object rhs,
                                  BigInteger bigi)
Given a BigInteger, narrow it to an Integer or Long if it fits and the arguments class allow it.

The rules are: if either arguments is a BigInteger, no narrowing will occur if either arguments is a Long, no narrowing to Integer will occur

Parameters:
lhs - the left hand side operand that lead to the bigi result
rhs - the right hand side operand that lead to the bigi result
bigi - the BigInteger to narrow
Returns:
an Integer or Long if narrowing is possible, the original BigInteger otherwise

narrowBigDecimal

protected Number narrowBigDecimal(Object lhs,
                                  Object rhs,
                                  BigDecimal bigd)
Given a BigDecimal, attempt to narrow it to an Integer or Long if it fits if one of the arguments is a numberable.

Parameters:
lhs - the left hand side operand that lead to the bigd result
rhs - the right hand side operand that lead to the bigd result
bigd - the BigDecimal to narrow
Returns:
an Integer or Long if narrowing is possible, the original BigInteger otherwise

narrowArguments

public boolean narrowArguments(Object[] args)
Replace all numbers in an arguments array with the smallest type that will fit.

Parameters:
args - the argument array
Returns:
true if some arguments were narrowed and args array is modified, false if no narrowing occurred and args array has not been modified

add

public Object add(Object left,
                  Object right)
Add two values together.

If any numeric add fails on coercion to the appropriate type, treat as Strings and do concatenation.

Parameters:
left - left argument
right - right argument
Returns:
left + right.

divide

public Object divide(Object left,
                     Object right)
Divide the left value by the right.

Parameters:
left - left argument
right - right argument
Returns:
left / right
Throws:
ArithmeticException - if right == 0

mod

public Object mod(Object left,
                  Object right)
left value modulo right.

Parameters:
left - left argument
right - right argument
Returns:
left % right
Throws:
ArithmeticException - if right == 0.0

multiply

public Object multiply(Object left,
                       Object right)
Multiply the left value by the right.

Parameters:
left - left argument
right - right argument
Returns:
left * right.

subtract

public Object subtract(Object left,
                       Object right)
Subtract the right value from the left.

Parameters:
left - left argument
right - right argument
Returns:
left - right.

negate

public Object negate(Object val)
Negates a value (unary minus for numbers).

Parameters:
val - the value to negate
Returns:
the negated value

contains

public Boolean contains(Object container,
                        Object value)
Test if left contains right (right matches/in left).

Beware that this method arguments are the opposite of the operator arguments. 'x in y' means 'y contains x'.

Parameters:
container - the container
value - the value
Returns:
test result or null if there is no arithmetic solution

endsWith

public Boolean endsWith(Object left,
                        Object right)
Test if left ends with right.

Parameters:
left - left argument
right - right argument
Returns:
left $= right if there is no arithmetic solution

startsWith

public Boolean startsWith(Object left,
                          Object right)
Test if left starts with right.

Parameters:
left - left argument
right - right argument
Returns:
left ^= right or null if there is no arithmetic solution

isEmpty

public Boolean isEmpty(Object object)
Check for emptyness of various types: Number, Collection, Array, Map, String.

Parameters:
object - the object to check the emptyness of
Returns:
the boolean or null of there is no arithmetic solution

size

public Integer size(Object object)
Calculate the size of various types: Collection, Array, Map, String.

Parameters:
object - the object to get the size of
Returns:
the size of object or null if there is no arithmetic solution

and

public Object and(Object left,
                  Object right)
Performs a bitwise and.

Parameters:
left - the left operand
right - the right operator
Returns:
left & right

or

public Object or(Object left,
                 Object right)
Performs a bitwise or.

Parameters:
left - the left operand
right - the right operator
Returns:
left | right

xor

public Object xor(Object left,
                  Object right)
Performs a bitwise xor.

Parameters:
left - the left operand
right - the right operator
Returns:
left ^ right

complement

public Object complement(Object val)
Performs a bitwise complement.

Parameters:
val - the operand
Returns:
~val

not

public Object not(Object val)
Performs a logical not.

Parameters:
val - the operand
Returns:
!val

compare

protected int compare(Object left,
                      Object right,
                      String operator)
Performs a comparison.

Parameters:
left - the left operand
right - the right operator
operator - the operator
Returns:
-1 if left < right; +1 if left > right; 0 if left == right
Throws:
ArithmeticException - if either left or right is null

equals

public boolean equals(Object left,
                      Object right)
Test if left and right are equal.

Parameters:
left - left argument
right - right argument
Returns:
the test result

lessThan

public boolean lessThan(Object left,
                        Object right)
Test if left < right.

Parameters:
left - left argument
right - right argument
Returns:
the test result

greaterThan

public boolean greaterThan(Object left,
                           Object right)
Test if left > right.

Parameters:
left - left argument
right - right argument
Returns:
the test result

lessThanOrEqual

public boolean lessThanOrEqual(Object left,
                               Object right)
Test if left <= right.

Parameters:
left - left argument
right - right argument
Returns:
the test result

greaterThanOrEqual

public boolean greaterThanOrEqual(Object left,
                                  Object right)
Test if left >= right.

Parameters:
left - left argument
right - right argument
Returns:
the test result

toBoolean

public boolean toBoolean(Object val)
Coerce to a primitive boolean.

Double.NaN, null, "false" and empty string coerce to false.

Parameters:
val - value to coerce
Returns:
the boolean value if coercion is possible, true if value was not null.

toInteger

public int toInteger(Object val)
Coerce to a primitive int.

Double.NaN, null and empty string coerce to zero.

Boolean false is 0, true is 1.

Parameters:
val - value to coerce
Returns:
the value coerced to int
Throws:
ArithmeticException - if val is null and mode is strict or if coercion is not possible

toLong

public long toLong(Object val)
Coerce to a primitive long.

Double.NaN, null and empty string coerce to zero.

Boolean false is 0, true is 1.

Parameters:
val - value to coerce
Returns:
the value coerced to long
Throws:
ArithmeticException - if value is null and mode is strict or if coercion is not possible

toBigInteger

public BigInteger toBigInteger(Object val)
Coerce to a BigInteger.

Double.NaN, null and empty string coerce to zero.

Boolean false is 0, true is 1.

Parameters:
val - the object to be coerced.
Returns:
a BigDecimal
Throws:
ArithmeticException - if val is null and mode is strict or if coercion is not possible

toBigDecimal

public BigDecimal toBigDecimal(Object val)
Coerce to a BigDecimal.

Double.NaN, null and empty string coerce to zero.

Boolean false is 0, true is 1.

Parameters:
val - the object to be coerced.
Returns:
a BigDecimal.
Throws:
ArithmeticException - if val is null and mode is strict or if coercion is not possible

toDouble

public double toDouble(Object val)
Coerce to a primitive double.

Double.NaN, null and empty string coerce to zero.

Boolean false is 0, true is 1.

Parameters:
val - value to coerce.
Returns:
The double coerced value.
Throws:
ArithmeticException - if val is null and mode is strict or if coercion is not possible

toString

public String toString(Object val)
Coerce to a string.

Double.NaN coerce to the empty string.

Parameters:
val - value to coerce.
Returns:
The String coerced value.
Throws:
ArithmeticException - if val is null and mode is strict or if coercion is not possible

bitwiseAnd

@Deprecated
public final Object bitwiseAnd(Object lhs,
                                          Object rhs)
Deprecated. 

Use or overload and() instead.

Parameters:
lhs - left hand side
rhs - right hand side
Returns:
lhs & rhs
See Also:
and(java.lang.Object, java.lang.Object)

bitwiseOr

@Deprecated
public final Object bitwiseOr(Object lhs,
                                         Object rhs)
Deprecated. 

Use or overload or() instead.

Parameters:
lhs - left hand side
rhs - right hand side
Returns:
lhs | rhs
See Also:
or(java.lang.Object, java.lang.Object)

bitwiseXor

@Deprecated
public final Object bitwiseXor(Object lhs,
                                          Object rhs)
Deprecated. 

Use or overload xor() instead.

Parameters:
lhs - left hand side
rhs - right hand side
Returns:
lhs ^ rhs
See Also:
xor(java.lang.Object, java.lang.Object)

logicalNot

@Deprecated
public final Object logicalNot(Object arg)
Deprecated. 

Use or overload not() instead.

Parameters:
arg - argument
Returns:
!arg
See Also:
not(java.lang.Object)

matches

@Deprecated
public final Object matches(Object lhs,
                                       Object rhs)
Deprecated. 

Use or overload contains() instead.

Parameters:
lhs - left hand side
rhs - right hand side
Returns:
contains(rhs, lhs)
See Also:
contains(java.lang.Object, java.lang.Object)


Copyright © 2001–2017 The Apache Software Foundation. All rights reserved.