Author: henrib
Date: Tue Sep  6 13:01:14 2011
New Revision: 1165652

URL: http://svn.apache.org/viewvc?rev=1165652&view=rev
Log:
Simplified arithmetic implementation using a general compare;
Added some checks wrt / 0 (% 0);

Modified:
    
commons/proper/jexl/trunk/src/main/java/org/apache/commons/jexl2/JexlArithmetic.java

Modified: 
commons/proper/jexl/trunk/src/main/java/org/apache/commons/jexl2/JexlArithmetic.java
URL: 
http://svn.apache.org/viewvc/commons/proper/jexl/trunk/src/main/java/org/apache/commons/jexl2/JexlArithmetic.java?rev=1165652&r1=1165651&r2=1165652&view=diff
==============================================================================
--- 
commons/proper/jexl/trunk/src/main/java/org/apache/commons/jexl2/JexlArithmetic.java
 (original)
+++ 
commons/proper/jexl/trunk/src/main/java/org/apache/commons/jexl2/JexlArithmetic.java
 Tue Sep  6 13:01:14 2011
@@ -404,6 +404,9 @@ public class JexlArithmetic {
         if (left instanceof BigDecimal || right instanceof BigDecimal) {
             BigDecimal l = toBigDecimal(left);
             BigDecimal r = toBigDecimal(right);
+            if (BigDecimal.ZERO.equals(r)) {
+                throw new ArithmeticException("/");
+            }
             BigDecimal result = l.divide(r, getMathContext());
             return narrowBigDecimal(left, right, result);
         }
@@ -411,6 +414,9 @@ public class JexlArithmetic {
         // otherwise treat as integers
         BigInteger l = toBigInteger(left);
         BigInteger r = toBigInteger(right);
+        if (BigInteger.ZERO.equals(r)) {
+            throw new ArithmeticException("/");
+        }
         BigInteger result = l.divide(r);
         return narrowBigInteger(left, right, result);
     }
@@ -441,6 +447,9 @@ public class JexlArithmetic {
         if (left instanceof BigDecimal || right instanceof BigDecimal) {
             BigDecimal l = toBigDecimal(left);
             BigDecimal r = toBigDecimal(right);
+            if (BigDecimal.ZERO.equals(r)) {
+                throw new ArithmeticException("%");
+            }
             BigDecimal remainder = l.remainder(r, getMathContext());
             return narrowBigDecimal(left, right, remainder);
         }
@@ -449,6 +458,9 @@ public class JexlArithmetic {
         BigInteger l = toBigInteger(left);
         BigInteger r = toBigInteger(right);
         BigInteger result = l.mod(r);
+        if (BigInteger.ZERO.equals(r)) {
+            throw new ArithmeticException("%");
+        }
         return narrowBigInteger(left, right, result);
     }
 
@@ -524,32 +536,34 @@ public class JexlArithmetic {
      * @return the negated value
      */
     public Object negate(Object val) {
-        if (val instanceof Byte) {
-            byte valueAsByte = ((Byte) val).byteValue();
-            return Byte.valueOf((byte) -valueAsByte);
-        } else if (val instanceof Short) {
-            short valueAsShort = ((Short) val).shortValue();
-            return Short.valueOf((short) -valueAsShort);
-        } else if (val instanceof Integer) {
+        if (val instanceof Integer) {
             int valueAsInt = ((Integer) val).intValue();
             return Integer.valueOf(-valueAsInt);
-        } else if (val instanceof Long) {
-            long valueAsLong = -((Long) val).longValue();
-            return Long.valueOf(valueAsLong);
-        } else if (val instanceof Float) {
-            float valueAsFloat = ((Float) val).floatValue();
-            return new Float(-valueAsFloat);
         } else if (val instanceof Double) {
             double valueAsDouble = ((Double) val).doubleValue();
             return new Double(-valueAsDouble);
+        } else if (val instanceof Long) {
+            long valueAsLong = -((Long) val).longValue();
+            return Long.valueOf(valueAsLong);
         } else if (val instanceof BigDecimal) {
             BigDecimal valueAsBigD = (BigDecimal) val;
             return valueAsBigD.negate();
         } else if (val instanceof BigInteger) {
             BigInteger valueAsBigI = (BigInteger) val;
             return valueAsBigI.negate();
+        } else if (val instanceof Float) {
+            float valueAsFloat = ((Float) val).floatValue();
+            return new Float(-valueAsFloat);
+        } else if (val instanceof Short) {
+            short valueAsShort = ((Short) val).shortValue();
+            return Short.valueOf((short) -valueAsShort);
+        } else if (val instanceof Byte) {
+            byte valueAsByte = ((Byte) val).byteValue();
+            return Byte.valueOf((byte) -valueAsByte);
+        } else if (val instanceof Boolean) {
+            return ((Boolean) val).booleanValue()? Boolean.FALSE : 
Boolean.TRUE;
         }
-        throw new IllegalArgumentException(val.toString() + ": negate can only 
be applied to a number");
+        throw new ArithmeticException("Object negation:(" + val + ")");
     }
 
     /**
@@ -577,6 +591,60 @@ public class JexlArithmetic {
     }
 
     /**
+     * Performs a comparison.
+     * @param left the left operand
+     * @param right the right operator
+     * @param operator the operator
+     * @return -1 if left  < right; +1 if left &gt > right; 0 if left == 
right
+     */
+    protected int compare(Object left, Object right, String operator) {
+        if (left != null && right != null) {
+            if (left instanceof BigDecimal || right instanceof BigDecimal) {
+                BigDecimal l = toBigDecimal(left);
+                BigDecimal r = toBigDecimal(right);
+                return l.compareTo(r);
+            } else if (left instanceof BigInteger || right instanceof 
BigInteger) {
+                BigInteger l = toBigInteger(left);
+                BigInteger r = toBigInteger(right);
+                return l.compareTo(r);
+            } else if (isFloatingPoint(left) || isFloatingPoint(right)) {
+                double lhs = toDouble(left);
+                double rhs = toDouble(right);
+                if (lhs < rhs) {
+                    return -1;
+                } else if (lhs > rhs) {
+                    return +1;
+                } else {
+                    return 0;
+                }
+            } else if (isNumberable(left) || isNumberable(right)) {
+                long lhs = toLong(left);
+                long rhs = toLong(right);
+                if (lhs < rhs) {
+                    return -1;
+                } else if (lhs > rhs) {
+                    return +1;
+                } else {
+                    return 0;
+                }
+            } else if (left instanceof String || right instanceof String) {
+                return toString(left).compareTo(toString(right));
+            } else if ("==".equals(operator)) {
+                return left.equals(right) ? 0 : -1;
+            } else if (left instanceof Comparable<?>) {
+                @SuppressWarnings("unchecked") // OK because of instanceof 
check above
+                final Comparable<Object> comparable = (Comparable<Object>) 
left;
+                return comparable.compareTo(right);
+            } else if (right instanceof Comparable<?>) {
+                @SuppressWarnings("unchecked") // OK because of instanceof 
check above
+                final Comparable<Object> comparable = (Comparable<Object>) 
right;
+                return comparable.compareTo(left);
+            }
+        }
+        throw new ArithmeticException("Object comparison:(" + left + " " + 
operator + " " + right + ")");
+    }
+
+    /**
      * Test if left and right are equal.
      *
      * @param left first value
@@ -584,34 +652,15 @@ public class JexlArithmetic {
      * @return test result.
      */
     public boolean equals(Object left, Object right) {
-        if (left == null && right == null) {
-            /*
-             * if both are null L == R
-             */
+        if (left == right) {
             return true;
         } else if (left == null || right == null) {
-            /*
-             * we know both aren't null, therefore L != R
-             */
             return false;
-        } else if (left instanceof BigDecimal || right instanceof BigDecimal) {
-            BigDecimal lhs = toBigDecimal(left);
-            BigDecimal rhs = toBigDecimal(right);
-            return lhs.compareTo(rhs) == 0;
-        } else if (left.getClass().equals(right.getClass())) {
-            return left.equals(right);
-        } else if (isFloatingPointType(left, right)) {
-            return toDouble(left) == toDouble(right);
-        } else if ((left instanceof Number || left instanceof Character)
-                && (right instanceof Character || right instanceof Number)) {
-            return toLong(left) == toLong(right);
         } else if (left instanceof Boolean || right instanceof Boolean) {
             return toBoolean(left) == toBoolean(right);
-        } else if (left instanceof java.lang.String || right instanceof 
String) {
-            return left.toString().equals(right.toString());
+        } else {
+            return compare(left, right, "==") == 0;
         }
-
-        return left.equals(right);
     }
 
     /**
@@ -624,35 +673,10 @@ public class JexlArithmetic {
     public boolean lessThan(Object left, Object right) {
         if ((left == right) || (left == null) || (right == null)) {
             return false;
-        } else if (isFloatingPoint(left) || isFloatingPoint(right)) {
-            double leftDouble = toDouble(left);
-            double rightDouble = toDouble(right);
-            return leftDouble < rightDouble;
-        } else if (left instanceof BigDecimal || right instanceof BigDecimal) {
-            BigDecimal l = toBigDecimal(left);
-            BigDecimal r = toBigDecimal(right);
-            return l.compareTo(r) < 0;
-        } else if (isNumberable(left) || isNumberable(right)) {
-            long leftLong = toLong(left);
-            long rightLong = toLong(right);
-            return leftLong < rightLong;
-        } else if (left instanceof String || right instanceof String) {
-            String leftString = left.toString();
-            String rightString = right.toString();
-            return leftString.compareTo(rightString) < 0;
-        } else if (left instanceof Comparable<?>) {
-            @SuppressWarnings("unchecked") // OK because of instanceof check 
above
-            final Comparable<Object> comparable = (Comparable<Object>) left;
-            return comparable.compareTo(right) < 0;
-        } else if (right instanceof Comparable<?>) {
-            @SuppressWarnings("unchecked") // OK because of instanceof check 
above
-            final Comparable<Object> comparable = (Comparable<Object>) right;
-            return comparable.compareTo(left) > 0;
+        } else {
+            return compare(left, right, "<") < 0;
         }
 
-        throw new IllegalArgumentException("Invalid comparison : comparing 
cardinality for left: " + left
-                + " and right: " + right);
-
     }
 
     /**
@@ -663,10 +687,11 @@ public class JexlArithmetic {
      * @return test result.
      */
     public boolean greaterThan(Object left, Object right) {
-        if (left == null || right == null) {
+        if ((left == right) || left == null || right == null) {
             return false;
+        } else {
+            return compare(left, right, ">") > 0;
         }
-        return !equals(left, right) && !lessThan(left, right);
     }
 
     /**
@@ -677,7 +702,13 @@ public class JexlArithmetic {
      * @return test result.
      */
     public boolean lessThanOrEqual(Object left, Object right) {
-        return equals(left, right) || lessThan(left, right);
+        if (left == right) {
+            return true;
+        } else if (left == null || right == null) {
+            return false;
+        } else {
+            return compare(left, right, "<=") <= 0;
+        }
     }
 
     /**
@@ -688,7 +719,13 @@ public class JexlArithmetic {
      * @return test result.
      */
     public boolean greaterThanOrEqual(Object left, Object right) {
-        return equals(left, right) || greaterThan(left, right);
+        if (left == right) {
+            return true;
+        } else if (left == null || right == null) {
+            return false;
+        } else {
+            return compare(left, right, ">=") >= 0;
+        }
     }
 
     /**
@@ -729,7 +766,7 @@ public class JexlArithmetic {
             } else {
                 return ((Double) val).intValue();
             }
-        }  else if (val instanceof Number) {
+        } else if (val instanceof Number) {
             return ((Number) val).intValue();
         } else if (val instanceof String) {
             if ("".equals(val)) {
@@ -742,8 +779,8 @@ public class JexlArithmetic {
             return ((Character) val).charValue();
         }
 
-        throw new IllegalArgumentException("Integer coercion exception. Can't 
coerce type: "
-                + val.getClass().getName());
+        throw new ArithmeticException("Integer coercion: "
+                + val.getClass().getName() + ":(" +val+")");
     }
 
     /**
@@ -776,7 +813,8 @@ public class JexlArithmetic {
             return ((Character) val).charValue();
         }
 
-        throw new IllegalArgumentException("Long coercion exception. Can't 
coerce type: " + val.getClass().getName());
+        throw new ArithmeticException("Long coercion: "
+                + val.getClass().getName() + ":(" +val+")");
     }
 
     /**
@@ -807,13 +845,13 @@ public class JexlArithmetic {
             } else {
                 return new BigInteger(string);
             }
-        }else if (val instanceof Character) {
+        } else if (val instanceof Character) {
             int i = ((Character) val).charValue();
             return BigInteger.valueOf(i);
         }
 
-        throw new IllegalArgumentException("BigInteger coercion exception. 
Can't coerce type: "
-                + val.getClass().getName());
+        throw new ArithmeticException("BigInteger coercion: "
+                + val.getClass().getName() + ":(" +val+")");
     }
 
     /**
@@ -848,8 +886,8 @@ public class JexlArithmetic {
             return new BigDecimal(i);
         }
 
-        throw new IllegalArgumentException("BigDecimal coercion exception. 
Can't coerce type: "
-                + val.getClass().getName());
+        throw new ArithmeticException("BigDecimal coercion: "
+                + val.getClass().getName() + ":(" +val+")");
     }
 
     /**
@@ -884,8 +922,8 @@ public class JexlArithmetic {
             return i;
         }
 
-        throw new IllegalArgumentException("Double coercion exception. Can't 
coerce type: "
-                + val.getClass().getName());
+        throw new ArithmeticException("Double coercion: "
+                + val.getClass().getName() + ":(" +val+")");
     }
 
     /**


Reply via email to