1 /* 2 * Copyright 2002-2008 the original author or authors. 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package org.springframework.util; 18 19 import java.math.BigDecimal; 20 import java.math.BigInteger; 21 import java.text.NumberFormat; 22 import java.util.Locale; 23 24 import junit.framework.TestCase; 25 26 import org.springframework.core.JdkVersion; 27 28 /** 29 * @author Rob Harrop 30 * @author Juergen Hoeller 31 */ 32 public class NumberUtilsTests extends TestCase { 33 testParseNumber()34 public void testParseNumber() { 35 String aByte = "" + Byte.MAX_VALUE; 36 String aShort = "" + Short.MAX_VALUE; 37 String anInteger = "" + Integer.MAX_VALUE; 38 String aLong = "" + Long.MAX_VALUE; 39 String aFloat = "" + Float.MAX_VALUE; 40 String aDouble = "" + Double.MAX_VALUE; 41 42 assertEquals("Byte did not parse", new Byte(Byte.MAX_VALUE), NumberUtils.parseNumber(aByte, Byte.class)); 43 assertEquals("Short did not parse", new Short(Short.MAX_VALUE), NumberUtils.parseNumber(aShort, Short.class)); 44 assertEquals("Integer did not parse", new Integer(Integer.MAX_VALUE), NumberUtils.parseNumber(anInteger, Integer.class)); 45 assertEquals("Long did not parse", new Long(Long.MAX_VALUE), NumberUtils.parseNumber(aLong, Long.class)); 46 assertEquals("Float did not parse", new Float(Float.MAX_VALUE), NumberUtils.parseNumber(aFloat, Float.class)); 47 assertEquals("Double did not parse", new Double(Double.MAX_VALUE), NumberUtils.parseNumber(aDouble, Double.class)); 48 } 49 testParseNumberUsingNumberFormat()50 public void testParseNumberUsingNumberFormat() { 51 NumberFormat nf = NumberFormat.getNumberInstance(Locale.US); 52 String aByte = "" + Byte.MAX_VALUE; 53 String aShort = "" + Short.MAX_VALUE; 54 String anInteger = "" + Integer.MAX_VALUE; 55 String aLong = "" + Long.MAX_VALUE; 56 String aFloat = "" + Float.MAX_VALUE; 57 String aDouble = "" + Double.MAX_VALUE; 58 59 assertEquals("Byte did not parse", new Byte(Byte.MAX_VALUE), NumberUtils.parseNumber(aByte, Byte.class, nf)); 60 assertEquals("Short did not parse", new Short(Short.MAX_VALUE), NumberUtils.parseNumber(aShort, Short.class, nf)); 61 assertEquals("Integer did not parse", new Integer(Integer.MAX_VALUE), NumberUtils.parseNumber(anInteger, Integer.class, nf)); 62 assertEquals("Long did not parse", new Long(Long.MAX_VALUE), NumberUtils.parseNumber(aLong, Long.class, nf)); 63 assertEquals("Float did not parse", new Float(Float.MAX_VALUE), NumberUtils.parseNumber(aFloat, Float.class, nf)); 64 assertEquals("Double did not parse", new Double(Double.MAX_VALUE), NumberUtils.parseNumber(aDouble, Double.class, nf)); 65 } 66 testParseWithTrim()67 public void testParseWithTrim() { 68 String aByte = " " + Byte.MAX_VALUE + " "; 69 String aShort = " " + Short.MAX_VALUE + " "; 70 String anInteger = " " + Integer.MAX_VALUE + " "; 71 String aLong = " " + Long.MAX_VALUE + " "; 72 String aFloat = " " + Float.MAX_VALUE + " "; 73 String aDouble = " " + Double.MAX_VALUE + " "; 74 75 assertEquals("Byte did not parse", new Byte(Byte.MAX_VALUE), NumberUtils.parseNumber(aByte, Byte.class)); 76 assertEquals("Short did not parse", new Short(Short.MAX_VALUE), NumberUtils.parseNumber(aShort, Short.class)); 77 assertEquals("Integer did not parse", new Integer(Integer.MAX_VALUE), NumberUtils.parseNumber(anInteger, Integer.class)); 78 assertEquals("Long did not parse", new Long(Long.MAX_VALUE), NumberUtils.parseNumber(aLong, Long.class)); 79 assertEquals("Float did not parse", new Float(Float.MAX_VALUE), NumberUtils.parseNumber(aFloat, Float.class)); 80 assertEquals("Double did not parse", new Double(Double.MAX_VALUE), NumberUtils.parseNumber(aDouble, Double.class)); 81 } 82 testParseWithTrimUsingNumberFormat()83 public void testParseWithTrimUsingNumberFormat() { 84 NumberFormat nf = NumberFormat.getNumberInstance(Locale.US); 85 String aByte = " " + Byte.MAX_VALUE + " "; 86 String aShort = " " + Short.MAX_VALUE + " "; 87 String anInteger = " " + Integer.MAX_VALUE + " "; 88 String aLong = " " + Long.MAX_VALUE + " "; 89 String aFloat = " " + Float.MAX_VALUE + " "; 90 String aDouble = " " + Double.MAX_VALUE + " "; 91 92 assertEquals("Byte did not parse", new Byte(Byte.MAX_VALUE), NumberUtils.parseNumber(aByte, Byte.class, nf)); 93 assertEquals("Short did not parse", new Short(Short.MAX_VALUE), NumberUtils.parseNumber(aShort, Short.class, nf)); 94 assertEquals("Integer did not parse", new Integer(Integer.MAX_VALUE), NumberUtils.parseNumber(anInteger, Integer.class, nf)); 95 assertEquals("Long did not parse", new Long(Long.MAX_VALUE), NumberUtils.parseNumber(aLong, Long.class, nf)); 96 assertEquals("Float did not parse", new Float(Float.MAX_VALUE), NumberUtils.parseNumber(aFloat, Float.class, nf)); 97 assertEquals("Double did not parse", new Double(Double.MAX_VALUE), NumberUtils.parseNumber(aDouble, Double.class, nf)); 98 } 99 testParseAsHex()100 public void testParseAsHex() { 101 String aByte = "0x" + Integer.toHexString(new Byte(Byte.MAX_VALUE).intValue()); 102 String aShort = "0x" + Integer.toHexString(new Short(Short.MAX_VALUE).intValue()); 103 String anInteger = "0x" + Integer.toHexString(Integer.MAX_VALUE); 104 String aLong = "0x" + Long.toHexString(Long.MAX_VALUE); 105 String aReallyBigInt = "FEBD4E677898DFEBFFEE44"; 106 107 assertByteEquals(aByte); 108 assertShortEquals(aShort); 109 assertIntegerEquals(anInteger); 110 assertLongEquals(aLong); 111 assertEquals("BigInteger did not parse", 112 new BigInteger(aReallyBigInt, 16), NumberUtils.parseNumber("0x" + aReallyBigInt, BigInteger.class)); 113 } 114 testParseNegativeHex()115 public void testParseNegativeHex() { 116 String aByte = "-0x80"; 117 String aShort = "-0x8000"; 118 String anInteger = "-0x80000000"; 119 String aLong = "-0x8000000000000000"; 120 String aReallyBigInt = "FEBD4E677898DFEBFFEE44"; 121 122 assertNegativeByteEquals(aByte); 123 assertNegativeShortEquals(aShort); 124 assertNegativeIntegerEquals(anInteger); 125 assertNegativeLongEquals(aLong); 126 assertEquals("BigInteger did not parse", 127 new BigInteger(aReallyBigInt, 16).negate(), NumberUtils.parseNumber("-0x" + aReallyBigInt, BigInteger.class)); 128 } 129 testDoubleToBigInteger()130 public void testDoubleToBigInteger() { 131 Double decimal = new Double(3.14d); 132 assertEquals(new BigInteger("3"), NumberUtils.convertNumberToTargetClass(decimal, BigInteger.class)); 133 } 134 testBigDecimalToBigInteger()135 public void testBigDecimalToBigInteger() { 136 String number = "987459837583750387355346"; 137 BigDecimal decimal = new BigDecimal(number); 138 assertEquals(new BigInteger(number), NumberUtils.convertNumberToTargetClass(decimal, BigInteger.class)); 139 } 140 testNonExactBigDecimalToBigInteger()141 public void testNonExactBigDecimalToBigInteger() { 142 BigDecimal decimal = new BigDecimal("987459837583750387355346.14"); 143 assertEquals(new BigInteger("987459837583750387355346"), NumberUtils.convertNumberToTargetClass(decimal, BigInteger.class)); 144 } 145 testParseBigDecimalNumber1()146 public void testParseBigDecimalNumber1() { 147 String bigDecimalAsString = "0.10"; 148 Number bigDecimal = NumberUtils.parseNumber(bigDecimalAsString, BigDecimal.class); 149 assertEquals(new BigDecimal(bigDecimalAsString), bigDecimal); 150 } 151 testParseBigDecimalNumber2()152 public void testParseBigDecimalNumber2() { 153 String bigDecimalAsString = "0.001"; 154 Number bigDecimal = NumberUtils.parseNumber(bigDecimalAsString, BigDecimal.class); 155 assertEquals(new BigDecimal(bigDecimalAsString), bigDecimal); 156 } 157 testParseBigDecimalNumber3()158 public void testParseBigDecimalNumber3() { 159 String bigDecimalAsString = "3.14159265358979323846"; 160 Number bigDecimal = NumberUtils.parseNumber(bigDecimalAsString, BigDecimal.class); 161 assertEquals(new BigDecimal(bigDecimalAsString), bigDecimal); 162 } 163 testParseLocalizedBigDecimalNumber1()164 public void testParseLocalizedBigDecimalNumber1() { 165 if (JdkVersion.getMajorJavaVersion() < JdkVersion.JAVA_15) { 166 return; 167 } 168 String bigDecimalAsString = "0.10"; 169 NumberFormat numberFormat = NumberFormat.getInstance(Locale.ENGLISH); 170 Number bigDecimal = NumberUtils.parseNumber(bigDecimalAsString, BigDecimal.class, numberFormat); 171 assertEquals(new BigDecimal(bigDecimalAsString), bigDecimal); 172 } 173 testParseLocalizedBigDecimalNumber2()174 public void testParseLocalizedBigDecimalNumber2() { 175 if (JdkVersion.getMajorJavaVersion() < JdkVersion.JAVA_15) { 176 return; 177 } 178 String bigDecimalAsString = "0.001"; 179 NumberFormat numberFormat = NumberFormat.getInstance(Locale.ENGLISH); 180 Number bigDecimal = NumberUtils.parseNumber(bigDecimalAsString, BigDecimal.class, numberFormat); 181 assertEquals(new BigDecimal(bigDecimalAsString), bigDecimal); 182 } 183 testParseLocalizedBigDecimalNumber3()184 public void testParseLocalizedBigDecimalNumber3() { 185 if (JdkVersion.getMajorJavaVersion() < JdkVersion.JAVA_15) { 186 return; 187 } 188 String bigDecimalAsString = "3.14159265358979323846"; 189 NumberFormat numberFormat = NumberFormat.getInstance(Locale.ENGLISH); 190 Number bigDecimal = NumberUtils.parseNumber(bigDecimalAsString, BigDecimal.class, numberFormat); 191 assertEquals(new BigDecimal(bigDecimalAsString), bigDecimal); 192 } 193 testParseOverflow()194 public void testParseOverflow() { 195 String aLong = "" + Long.MAX_VALUE; 196 String aDouble = "" + Double.MAX_VALUE; 197 198 try { 199 NumberUtils.parseNumber(aLong, Byte.class); 200 fail("Should have thrown IllegalArgumentException"); 201 } 202 catch (IllegalArgumentException expected) { 203 } 204 205 try { 206 NumberUtils.parseNumber(aLong, Short.class); 207 fail("Should have thrown IllegalArgumentException"); 208 } 209 catch (IllegalArgumentException expected) { 210 } 211 212 try { 213 NumberUtils.parseNumber(aLong, Integer.class); 214 fail("Should have thrown IllegalArgumentException"); 215 } 216 catch (IllegalArgumentException expected) { 217 } 218 219 assertEquals(new Long(Long.MAX_VALUE), NumberUtils.parseNumber(aLong, Long.class)); 220 221 assertEquals(new Double(Double.MAX_VALUE), NumberUtils.parseNumber(aDouble, Double.class)); 222 } 223 testParseNegativeOverflow()224 public void testParseNegativeOverflow() { 225 String aLong = "" + Long.MIN_VALUE; 226 String aDouble = "" + Double.MIN_VALUE; 227 228 try { 229 NumberUtils.parseNumber(aLong, Byte.class); 230 fail("Should have thrown IllegalArgumentException"); 231 } 232 catch (IllegalArgumentException expected) { 233 } 234 235 try { 236 NumberUtils.parseNumber(aLong, Short.class); 237 fail("Should have thrown IllegalArgumentException"); 238 } 239 catch (IllegalArgumentException expected) { 240 } 241 242 try { 243 NumberUtils.parseNumber(aLong, Integer.class); 244 fail("Should have thrown IllegalArgumentException"); 245 } 246 catch (IllegalArgumentException expected) { 247 } 248 249 assertEquals(new Long(Long.MIN_VALUE), NumberUtils.parseNumber(aLong, Long.class)); 250 251 assertEquals(new Double(Double.MIN_VALUE), NumberUtils.parseNumber(aDouble, Double.class)); 252 } 253 testParseOverflowUsingNumberFormat()254 public void testParseOverflowUsingNumberFormat() { 255 NumberFormat nf = NumberFormat.getNumberInstance(Locale.US); 256 String aLong = "" + Long.MAX_VALUE; 257 String aDouble = "" + Double.MAX_VALUE; 258 259 try { 260 NumberUtils.parseNumber(aLong, Byte.class, nf); 261 fail("Should have thrown IllegalArgumentException"); 262 } 263 catch (IllegalArgumentException expected) { 264 } 265 266 try { 267 NumberUtils.parseNumber(aLong, Short.class, nf); 268 fail("Should have thrown IllegalArgumentException"); 269 } 270 catch (IllegalArgumentException expected) { 271 } 272 273 try { 274 NumberUtils.parseNumber(aLong, Integer.class, nf); 275 fail("Should have thrown IllegalArgumentException"); 276 } 277 catch (IllegalArgumentException expected) { 278 } 279 280 assertEquals(new Long(Long.MAX_VALUE), NumberUtils.parseNumber(aLong, Long.class, nf)); 281 282 assertEquals(new Double(Double.MAX_VALUE), NumberUtils.parseNumber(aDouble, Double.class, nf)); 283 } 284 testParseNegativeOverflowUsingNumberFormat()285 public void testParseNegativeOverflowUsingNumberFormat() { 286 NumberFormat nf = NumberFormat.getNumberInstance(Locale.US); 287 String aLong = "" + Long.MIN_VALUE; 288 String aDouble = "" + Double.MIN_VALUE; 289 290 try { 291 NumberUtils.parseNumber(aLong, Byte.class, nf); 292 fail("Should have thrown IllegalArgumentException"); 293 } 294 catch (IllegalArgumentException expected) { 295 } 296 297 try { 298 NumberUtils.parseNumber(aLong, Short.class, nf); 299 fail("Should have thrown IllegalArgumentException"); 300 } 301 catch (IllegalArgumentException expected) { 302 } 303 304 try { 305 NumberUtils.parseNumber(aLong, Integer.class, nf); 306 fail("Should have thrown IllegalArgumentException"); 307 } 308 catch (IllegalArgumentException expected) { 309 } 310 311 assertEquals(new Long(Long.MIN_VALUE), NumberUtils.parseNumber(aLong, Long.class, nf)); 312 313 assertEquals(new Double(Double.MIN_VALUE), NumberUtils.parseNumber(aDouble, Double.class, nf)); 314 } 315 assertLongEquals(String aLong)316 private void assertLongEquals(String aLong) { 317 assertEquals("Long did not parse", Long.MAX_VALUE, NumberUtils.parseNumber(aLong, Long.class).longValue()); 318 } 319 assertIntegerEquals(String anInteger)320 private void assertIntegerEquals(String anInteger) { 321 assertEquals("Integer did not parse", Integer.MAX_VALUE, NumberUtils.parseNumber(anInteger, Integer.class).intValue()); 322 } 323 assertShortEquals(String aShort)324 private void assertShortEquals(String aShort) { 325 assertEquals("Short did not parse", Short.MAX_VALUE, NumberUtils.parseNumber(aShort, Short.class).shortValue()); 326 } 327 assertByteEquals(String aByte)328 private void assertByteEquals(String aByte) { 329 assertEquals("Byte did not parse", Byte.MAX_VALUE, NumberUtils.parseNumber(aByte, Byte.class).byteValue()); 330 } 331 assertNegativeLongEquals(String aLong)332 private void assertNegativeLongEquals(String aLong) { 333 assertEquals("Long did not parse", Long.MIN_VALUE, NumberUtils.parseNumber(aLong, Long.class).longValue()); 334 } 335 assertNegativeIntegerEquals(String anInteger)336 private void assertNegativeIntegerEquals(String anInteger) { 337 assertEquals("Integer did not parse", Integer.MIN_VALUE, NumberUtils.parseNumber(anInteger, Integer.class).intValue()); 338 } 339 assertNegativeShortEquals(String aShort)340 private void assertNegativeShortEquals(String aShort) { 341 assertEquals("Short did not parse", Short.MIN_VALUE, NumberUtils.parseNumber(aShort, Short.class).shortValue()); 342 } 343 assertNegativeByteEquals(String aByte)344 private void assertNegativeByteEquals(String aByte) { 345 assertEquals("Byte did not parse", Byte.MIN_VALUE, NumberUtils.parseNumber(aByte, Byte.class).byteValue()); 346 } 347 348 } 349