经常能听到这个说法,甚至编程规范也会约束不让用String的split方法,那么是不是真的就很慢呢?测试代码如下
public static void main(String[] args)
{
String str = "abc:abc:drdf:dfw:da";
System.out.println(System.currentTimeMillis());
for (int i = 0; i < 10000000; i++)
{
String[] strArr1 = str.split(":");
}
System.out.println(System.currentTimeMillis());
for (int i = 0; i < 10000000; i++)
{
String[] strArr2 = StringUtils.split(str, ':');
}
System.out.println(System.currentTimeMillis());
}
运行环境win7 jdk1.8,分别耗时2746ms和2312ms,可以看出来是差不多的,那么jdk1.6上呢?分别耗时6375ms和1478ms,4倍多的差距,应该就是这个说法的源泉了。
那么jdk1.8到底做了什么让耗时变小的呢?从String.split()的注释可以看到
fastpath if the regex is a
(1)one-char String and this character is not one of the
RegEx's meta characters ".$|()[{^?*+\\", or
(2)two-char String and the first char is the backslash and
the second is not the ascii digit or ascii letter.
就是对我们常用的这种字符串分隔(包括非正则表达式字符的单个字符和反斜杠转移的双字符),做了提前处理,然后再进行正则表达式的匹配,所以速度快了不少。有感于江南白衣jvm调优的一份ppt,技术在不断的进步,很多以前的说法稍不注意就会过时,如同最早的null放在等号前、加号拼接字符串会变慢,都逐步的不是问题了,前人的总结指不定就过时了。