BUG-4638: Split out Number comparator 85/28585/13
authorRobert Varga <rovarga@cisco.com>
Tue, 20 Oct 2015 09:47:46 +0000 (11:47 +0200)
committerTony Tkacik <ttkacik@cisco.com>
Mon, 16 Nov 2015 11:35:06 +0000 (11:35 +0000)
Comapring two Numbers of the same class is useful also for comparing
lengths. Split it out into utility methods.

Change-Id: I0203d191a7849b7485419a5ef9e32c0fef442ed3
Signed-off-by: Robert Varga <rovarga@cisco.com>
yang/yang-model-util/src/main/java/org/opendaylight/yangtools/yang/model/util/type/NumberUtil.java
yang/yang-model-util/src/main/java/org/opendaylight/yangtools/yang/model/util/type/RangeRestrictedTypeBuilder.java

index 0d5e0b29c28551ce8b0307c97785343943191d18..2446ef0b82b71949dba336b2d4af1d891fe9c836 100644 (file)
@@ -8,12 +8,38 @@
 package org.opendaylight.yangtools.yang.model.util.type;
 
 import com.google.common.base.Function;
+import com.google.common.base.Preconditions;
 import com.google.common.collect.ImmutableMap;
 import java.math.BigDecimal;
 import java.math.BigInteger;
+import java.util.Comparator;
 import java.util.Map;
 
 final class NumberUtil {
+    private static final Comparator<Number> NUMBER_COMPARATOR = new Comparator<Number>() {
+        @Override
+        public int compare(final Number o1, final Number o2) {
+            Preconditions.checkArgument(o1.getClass().equals(o2.getClass()), "Incompatible Number classes %s and %s",
+                o1.getClass(), o2.getClass());
+
+            if (o1 instanceof Byte) {
+                return ((Byte)o1).compareTo((Byte) o2);
+            } else if (o1 instanceof Short) {
+                return ((Short)o1).compareTo((Short) o2);
+            } else if (o1 instanceof Integer) {
+                return ((Integer)o1).compareTo((Integer) o2);
+            } else if (o1 instanceof Long) {
+                return ((Long)o1).compareTo((Long) o2);
+            } else if (o1 instanceof BigDecimal) {
+                return ((BigDecimal)o1).compareTo((BigDecimal) o2);
+            } else if (o1 instanceof BigInteger) {
+                return ((BigInteger)o1).compareTo((BigInteger) o2);
+            } else {
+                throw new IllegalArgumentException("Unsupported Number class " + o1.getClass());
+            }
+        }
+    };
+
     private static final Map<Class<? extends Number>, Function<Number, Number>> CONVERTERS;
     static {
         final ImmutableMap.Builder<Class<? extends Number>, Function<Number, Number>> b = ImmutableMap.builder();
@@ -104,4 +130,9 @@ final class NumberUtil {
     static Function<Number, Number> converterTo(final Class<? extends Number> clazz) {
         return CONVERTERS.get(clazz);
     }
+
+    static boolean isRangeCovered(final Number min, final Number max, final Number superMin, final Number superMax) {
+        return NumberUtil.NUMBER_COMPARATOR.compare(min, superMin) >= 0 &&
+                NumberUtil.NUMBER_COMPARATOR.compare(max, superMax) <= 0;
+    }
 }
index 5954068913b8f22e14e0df41ff9d42d3f66bdfb8..f600ed5be9264053a37c1529fab84c489be422cd 100644 (file)
@@ -114,14 +114,8 @@ public abstract class RangeRestrictedTypeBuilder<T extends TypeDefinition<T>> ex
 
     private static boolean rangeCovered(final List<RangeConstraint> where,
             final RangeConstraint what) {
-        // We have ensured the types match, and we are sure each of those types implements comparable
-        @SuppressWarnings("unchecked")
-        final Comparable<Object> min = (Comparable<Object>) what.getMin();
-        @SuppressWarnings("unchecked")
-        final Comparable<Object> max = (Comparable<Object>) what.getMax();
-
         for (RangeConstraint c : where) {
-            if (min.compareTo(c.getMin()) >= 0 && max.compareTo(c.getMax()) <= 0) {
+            if (NumberUtil.isRangeCovered(what.getMin(), what.getMax(), c.getMin(), c.getMax())) {
                 return true;
             }
         }