2 * Copyright (c) 2015 Pantheon Technologies s.r.o. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
8 package org.opendaylight.yangtools.yang.model.ri.type;
10 import static com.google.common.base.Preconditions.checkArgument;
12 import com.google.common.collect.ImmutableMap;
13 import java.util.Comparator;
14 import java.util.function.Function;
15 import org.opendaylight.yangtools.yang.common.Decimal64;
16 import org.opendaylight.yangtools.yang.common.Uint16;
17 import org.opendaylight.yangtools.yang.common.Uint32;
18 import org.opendaylight.yangtools.yang.common.Uint64;
19 import org.opendaylight.yangtools.yang.common.Uint8;
21 final class NumberUtil {
22 private static final Comparator<Number> NUMBER_COMPARATOR = (o1, o2) -> {
23 checkArgument(o1.getClass().equals(o2.getClass()), "Incompatible Number classes %s and %s",
24 o1.getClass(), o2.getClass());
26 if (o1 instanceof Byte) {
27 return ((Byte)o1).compareTo((Byte) o2);
28 } else if (o1 instanceof Short) {
29 return ((Short)o1).compareTo((Short) o2);
30 } else if (o1 instanceof Integer) {
31 return ((Integer)o1).compareTo((Integer) o2);
32 } else if (o1 instanceof Long) {
33 return ((Long)o1).compareTo((Long) o2);
34 } else if (o1 instanceof Uint8) {
35 return ((Uint8)o1).compareTo((Uint8) o2);
36 } else if (o1 instanceof Uint16) {
37 return ((Uint16)o1).compareTo((Uint16) o2);
38 } else if (o1 instanceof Uint32) {
39 return ((Uint32)o1).compareTo((Uint32) o2);
40 } else if (o1 instanceof Uint64) {
41 return ((Uint64)o1).compareTo((Uint64) o2);
42 } else if (o1 instanceof Decimal64) {
43 return ((Decimal64)o1).compareTo((Decimal64) o2);
45 throw new IllegalArgumentException("Unsupported Number class " + o1.getClass());
49 private static final ImmutableMap<Class<? extends Number>, Function<Number, Number>> CONVERTERS;
52 final ImmutableMap.Builder<Class<? extends Number>, Function<Number, Number>> b = ImmutableMap.builder();
53 b.put(Byte.class, input -> {
54 if (input instanceof Byte) {
58 return Byte.valueOf(input.toString());
60 b.put(Short.class, input -> {
61 if (input instanceof Short) {
64 if (input instanceof Byte) {
65 return input.shortValue();
68 return Short.valueOf(input.toString());
70 b.put(Integer.class, input -> {
71 if (input instanceof Integer) {
74 if (input instanceof Byte || input instanceof Short) {
75 return input.intValue();
78 return Integer.valueOf(input.toString());
80 b.put(Long.class, input -> {
81 if (input instanceof Long) {
84 if (input instanceof Byte || input instanceof Short || input instanceof Integer) {
85 return input.longValue();
88 return Long.valueOf(input.toString());
90 b.put(Decimal64.class, input -> {
91 if (input instanceof Decimal64) {
94 if (input instanceof Byte || input instanceof Short || input instanceof Integer || input instanceof Long) {
95 // FIXME: this is not right, as we need to know fraction-digits
96 return Decimal64.valueOf(1, input.longValue());
99 return Decimal64.valueOf(input.toString());
101 b.put(Uint8.class, input -> {
102 if (input instanceof Uint8) {
105 // FIXME: revise this
106 if (input instanceof Byte || input instanceof Short || input instanceof Integer || input instanceof Long
107 || input instanceof Uint16 || input instanceof Uint32 || input instanceof Uint64) {
108 return Uint8.valueOf(input.longValue());
111 return Uint8.valueOf(input.toString());
113 b.put(Uint16.class, input -> {
114 if (input instanceof Uint16) {
117 // FIXME: revise this
118 if (input instanceof Byte || input instanceof Short || input instanceof Integer || input instanceof Long
119 || input instanceof Uint8 || input instanceof Uint32 || input instanceof Uint64) {
120 return Uint16.valueOf(input.longValue());
123 return Uint16.valueOf(input.toString());
125 b.put(Uint32.class, input -> {
126 if (input instanceof Uint32) {
129 // FIXME: revise this
130 if (input instanceof Byte || input instanceof Short || input instanceof Integer || input instanceof Long
131 || input instanceof Uint8 || input instanceof Uint16 || input instanceof Uint64) {
132 return Uint32.valueOf(input.longValue());
135 return Uint32.valueOf(input.toString());
137 b.put(Uint64.class, input -> {
138 if (input instanceof Uint64) {
141 // FIXME: revise this
142 if (input instanceof Byte || input instanceof Short || input instanceof Integer || input instanceof Long
143 || input instanceof Uint8 || input instanceof Uint16 || input instanceof Uint32) {
144 return Uint64.valueOf(input.longValue());
147 return Uint64.valueOf(input.toString());
149 CONVERTERS = b.build();
152 private NumberUtil() {
156 @SuppressWarnings("unchecked")
157 static <T extends Number> Function<Number, T> converterTo(final Class<T> clazz) {
158 return (Function<Number, T>) CONVERTERS.get(clazz);
161 static boolean isRangeCovered(final Number min, final Number max, final Number superMin, final Number superMax) {
162 return NumberUtil.NUMBER_COMPARATOR.compare(min, superMin) >= 0
163 && NumberUtil.NUMBER_COMPARATOR.compare(max, superMax) <= 0;