肯爹的 StringUtils.isNumeric(String str)

在项目中遇到一处bug,调试的结果竟然是StringUtils.isNumeric(String str) 在捣鬼(采用的是org.apache.commons.lang.StringUtils),下面的代码是判断一个参数非空,且为整数:

if(StringUtils.isNumeric(str) && StringUtils.isNotBlank(str)){
            // do sth
}

在简单不过的代码,却隐藏着bug !

因为如果 str = "-1"; StringUtils.isNumeric(str) 返回的是 false! 真是肯爹不偿命啊。

下面是测试:

public static void main(String[] args)
{
        System.out.println(StringUtils.isNumeric("-1"));
}

运行结果:false

肯爹吧?用正则表达式实现不是很简单吗?怎么会这样,看了下源码:

public static boolean isNumeric(String str) {
        if (str == null) {
            return false;
        }
        int sz = str.length();
        for (int i = 0; i < sz; i++) {
            if (Character.isDigit(str.charAt(i)) == false) {
                return false;
            }
        }
        return true;
 }

继续跳进去:

public static boolean isDigit(char ch) {
        return isDigit((int)ch);
}

继续:

public static boolean isDigit(int codePoint) {
        boolean bDigit = false;

        if (codePoint >= MIN_CODE_POINT && codePoint <= FAST_PATH_MAX) {
            bDigit = CharacterDataLatin1.isDigit(codePoint);
        } else {
            int plane = getPlane(codePoint);
            switch(plane) {
            case(0):
                bDigit = CharacterData00.isDigit(codePoint);
                break;
            case(1):
                bDigit = CharacterData01.isDigit(codePoint);
                break;
            case(2):
                bDigit = CharacterData02.isDigit(codePoint);
                break;
            case(3): // Undefined
            case(4): // Undefined
            case(5): // Undefined
            case(6): // Undefined
            case(7): // Undefined
            case(8): // Undefined
            case(9): // Undefined
            case(10): // Undefined
            case(11): // Undefined
            case(12): // Undefined
            case(13): // Undefined
                bDigit = CharacterDataUndefined.isDigit(codePoint);
                break;
            case(14):
                bDigit = CharacterData0E.isDigit(codePoint);
                break;
            case(15): // Private Use
            case(16): // Private Use
                bDigit = CharacterDataPrivateUse.isDigit(codePoint);
                break;
            default:
                // the argument‘s plane is invalid, and thus is an invalid codepoint
                // bDigit remains false;
                break;
            }
        }
        return bDigit;
    }

在下面一步失败:

 static boolean isDigit(int ch) {
        int type = getType(ch);
        return (type == Character.DECIMAL_DIGIT_NUMBER);
    }

也就是说他的实现完全没有考虑到 - + 前缀的问题,这不是傻叉吗?

下面的结果都是 false:

public static void main(String[] args)
{
        System.out.println(StringUtils.isNumeric("-1"));
        System.out.println(StringUtils.isNumeric("+1"));
}

这是他的方法注释:

Checks if the String contains only unicode digits. A decimal point is not a unicode digit and returns false.

null will return false. An empty String ("") will return true.

 StringUtils.isNumeric(null)   = false
 StringUtils.isNumeric("")     = true
 StringUtils.isNumeric("  ")   = false
 StringUtils.isNumeric("123")  = true
 StringUtils.isNumeric("12 3") = false
 StringUtils.isNumeric("ab2c") = false
 StringUtils.isNumeric("12-3") = false
 StringUtils.isNumeric("12.3") = false

Parameters:
str the String to check, may be null
Returns:
true if only contains digits, and is non-null

只能包含 unicode 的数字, +, -, . 三者都不能算作是unicode 数字。

时间: 2024-10-23 03:13:15

肯爹的 StringUtils.isNumeric(String str)的相关文章

StringUtils.isNumeric(String str) 的一个坑(转)

在项目中遇到一处bug,调试的结果竟然是StringUtils.isNumeric(String str) 在捣鬼(采用的是org.apache.commons.lang.StringUtils),下面的代码是判断一个参数非空,且为整数: if(StringUtils.isNumeric(str) && StringUtils.isNotBlank(str)){ // do sth } 在简单不过的代码,却隐藏着bug ! 因为如果 str = "-1"; String

POJ 1590 Palindromes 肯爹题

本题就是专门肯人的题目,给出的列子也是故意误导人的. 其实就考一点:没有mirror的字母存在的时候就可以判定整个字符串不是mirror! 如下面的mirrored string的叙述: A mirrored string is a string for which when each of the elements of the string is changed to its reverse (if it has a reverse) and the string is read backw

堆与栈(JAVA)——以String str=&quot;abc&quot;的深度含义解释

栈(stack)与堆(heap)都是Java用来在Ram中存放数据的地方.与C++不同,Java自动管理栈和堆,程序员不能直接地设置栈或堆. 栈的优势是,存取速度比堆要快,仅次于直接位于CPU中的寄存器.但缺点是,存在栈中的数据大小与生存期必须是确定的,缺乏灵活性.另外,栈数据在多个线程或者多个栈之间是不可以共享的,但是在栈内部多个值相等的变量是可以指向一个地址的.堆的优势是可以动态地分配内存大小,生存期也不必事先告诉编译器,Java的垃圾收集器会自动收走这些不再使用的数据.但缺点是,由于要在运

String str=new String(&quot;abc&quot;)到底创建了几个对象

这句代码到底创建了几个对象?研究了好一阵,现在才能说清楚. package com.sun.test; public class Test<T> { T a; /** * @param args */ public static void main(String[] args) { String str=new String("abc"); } } 我们来看下这段简单代码的字节码: <pre name="code" class="java

String str = new String(&quot;abc&quot;),这段代码一共生成了几个String对象?为什么?

String str = new String("abc")创建了俩个对象,首先为创建一个String对象"abc",然后在调用String类的构造方法时 1 public String(String original) { 2 //other code ... 3 } 再次创建了一个对象original,并把"abc"这个对象传给original,进而赋值给str. 所以一共创建了2个对象.

经典String str = new String(&quot;abc&quot;)内存分配问题

出自:http://blog.csdn.net/ycwload/article/details/2650059 今天要找和存储管理相关的一些知识,网上搜了半天也没有找到完善的(30%的程度都不到),没办法,下载了曾经大学里的一本pdf格式的教学书,看了整整一天才算是搞明白存储管理中的一部分知识.曾几何时,我曾写过大学无用的一些小论题,觉得大学里教的东西不切合实际,理论化偏严重,总认为用理论教出来的人,总是说着牛逼,做事掉渣的人.所以,在大学里,我的学习只能说是应付考试,太多的东西都没有去深入了解

compareTo(String str)与compareToIgnoreCase(String str)

一.compareTo(String str)方法 返回值:如果参数字符串等于此字符串,则返回值 0:如果此字符串按字典顺序小于字符串参数,则返回一个小于 0 的值:如果此字符串按字典顺序大于字符串参数,则返回一个大于 0 的值. 1.按字典顺序比较两个字符串 String str0 = "a"; String str1 = "b"; int result0 = str0.compareTo(str1);//-1 System.out.println("r

关于String str =new String(&quot;abc&quot;)和 String str = &quot;abc&quot;的比较

String是一个非常常用的类,应该深入的去了解String 如: String str =new String("abc") String str1 = "abc" System.out.println(str == str1) System.out.println(str.equal(str1)) 结果: false true 原因解析: Java运行环境有一个字符串池,由String类维护,执行语句String str="abc"时 1.

由String str=new String(&quot;abc&quot;);引起的

话题是由如下的事情引出的: public class StringTest { public static void main(String[] args) { String str1 = new String("abc"); String str2 = "abc"; if (str1 == str2) { System.out.println("str1 == str2"); } else { System.out.println("