This is an automated email from the ASF dual-hosted git repository.

garydgregory pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/commons-lang.git


The following commit(s) were added to refs/heads/master by this push:
     new fa59a3159 [LANG-1821] NumberUtils.isCreatable fails for hexadecimal 
numbers with long type qualifier (#1629)
fa59a3159 is described below

commit fa59a31596ce37abe09c5f058c6f2e035f7c6677
Author: Gary Gregory <[email protected]>
AuthorDate: Sat Apr 25 08:28:41 2026 -0400

    [LANG-1821] NumberUtils.isCreatable fails for hexadecimal numbers with long 
type qualifier (#1629)
    
    * Add testLang1641()
    
    * Rename some test methods
    
    * [LANG-1821] NumberUtils.isCreatable fails for hexadecimal numbers with
    long type qualifier
---
 .../org/apache/commons/lang3/math/NumberUtils.java | 11 ++++++++--
 .../apache/commons/lang3/math/NumberUtilsTest.java | 25 ++++++++++++++++++++++
 2 files changed, 34 insertions(+), 2 deletions(-)

diff --git a/src/main/java/org/apache/commons/lang3/math/NumberUtils.java 
b/src/main/java/org/apache/commons/lang3/math/NumberUtils.java
index 7327fac06..92b363a72 100644
--- a/src/main/java/org/apache/commons/lang3/math/NumberUtils.java
+++ b/src/main/java/org/apache/commons/lang3/math/NumberUtils.java
@@ -365,6 +365,7 @@ public static Number createNumber(final String str) {
                 break;
             }
         }
+        final char lastChar = str.charAt(length - 1);
         if (pfxLen > 0) { // we have a hex number
             char firstSigDigit = 0; // strip leading zeroes
             for (int i = pfxLen; i < length; i++) {
@@ -374,16 +375,22 @@ public static Number createNumber(final String str) {
                 }
                 pfxLen++;
             }
-            final int hexDigits = length - pfxLen;
+            final boolean isLongCh = lastChar == 'l' || lastChar == 'L';
+            int hexDigits = length - pfxLen;
+            if (isLongCh) {
+                hexDigits--;
+            }
             if (hexDigits > 16 || hexDigits == 16 && firstSigDigit > '7') { // 
too many for Long
                 return createBigInteger(str);
             }
+            if (isLongCh) {
+                return createLong(str.substring(0, str.length() - 1));
+            }
             if (hexDigits > 8 || hexDigits == 8 && firstSigDigit > '7') { // 
too many for an int
                 return createLong(str);
             }
             return createInteger(str);
         }
-        final char lastChar = str.charAt(length - 1);
         final String mant;
         final String dec;
         final String exp;
diff --git a/src/test/java/org/apache/commons/lang3/math/NumberUtilsTest.java 
b/src/test/java/org/apache/commons/lang3/math/NumberUtilsTest.java
index 49b89422c..16bdca67a 100644
--- a/src/test/java/org/apache/commons/lang3/math/NumberUtilsTest.java
+++ b/src/test/java/org/apache/commons/lang3/math/NumberUtilsTest.java
@@ -1232,6 +1232,31 @@ void testLang1729IsParsableShort() {
         assertFalse(isParsableShort("1 2 3"));
     }
 
+    /**
+     * Tests <a 
href="https://issues.apache.org/jira/browse/LANG-1821";>LANG-1821</a>.
+     */
+    @Test
+    void testLang1821() {
+        compareIsCreatableWithCreateNumber("123L", true);
+        compareIsCreatableWithCreateNumber("0xdef", true);
+        compareIsCreatableWithCreateNumber("0xdefL", true);
+        compareIsCreatableWithCreateNumber("0XDEFl", true);
+        // Integer.MAX_VALUE
+        compareIsCreatableWithCreateNumber("0x" + 
Integer.toHexString(Integer.MAX_VALUE), true);
+        compareIsCreatableWithCreateNumber("0x" + 
Integer.toHexString(Integer.MAX_VALUE) + "l", true);
+        compareIsCreatableWithCreateNumber("0x" + 
Integer.toHexString(Integer.MAX_VALUE) + "L", true);
+        compareIsCreatableWithCreateNumber("0X" + 
Integer.toHexString(Integer.MAX_VALUE), true);
+        compareIsCreatableWithCreateNumber("0X" + 
Integer.toHexString(Integer.MAX_VALUE) + "l", true);
+        compareIsCreatableWithCreateNumber("0X" + 
Integer.toHexString(Integer.MAX_VALUE) + "L", true);
+        // Long.MAX_VALUE
+        compareIsCreatableWithCreateNumber("0x" + 
Long.toHexString(Long.MAX_VALUE), true);
+        compareIsCreatableWithCreateNumber("0x" + 
Long.toHexString(Long.MAX_VALUE) + "l", true);
+        compareIsCreatableWithCreateNumber("0x" + 
Long.toHexString(Long.MAX_VALUE) + "L", true);
+        compareIsCreatableWithCreateNumber("0X" + 
Long.toHexString(Long.MAX_VALUE), true);
+        compareIsCreatableWithCreateNumber("0X" + 
Long.toHexString(Long.MAX_VALUE) + "l", true);
+        compareIsCreatableWithCreateNumber("0X" + 
Long.toHexString(Long.MAX_VALUE) + "L", true);
+    }
+
     @Test
     void testLang300() {
         NumberUtils.createNumber("-1l");

Reply via email to