当前位置: 首页 > 科技观察

为什么Java8不再需要StringBuilder来拼接字符串_0

时间:2023-03-15 11:46:24 科技观察

在Java开发者中,字符串拼接的高资源消耗常常是一个热门话题。  深入探讨一下为什么会占用高资源。在Java中,String对象是不可变的,这意味着它一旦创建就无法更改。所以当我们连接字符串时,一个新字符串被创建,旧字符串被垃圾收集器标记。  如果我们处理数百万个字符串,那么我们会生成数百万个额外的字符串以供垃圾收集器处理。  虚拟机底层在拼接字符串时进行了很多操作。用于连接字符串的最直接的点运算符是String#concat(String)操作。publicStringconcat(Stringstr){intotherLen=str.length();如果(otherLen==0){返回这个;}intlen=value.length;charbuf[]=Arrays.copyOf(value,len+otherLen);str.getChars(buf,len);returnnewString(buf,true);}publicstaticchar[]copyOf(char[]original,intnewLength){char[]copy=newchar[newLength];复制代码系统。arraycopy(原始,0,副本,0,Math.min(原始长度,newLength));returncopy;}voidgetChars(chardst[],intdstBegin){System.arraycopy(value,0,dst,dstBegin,value.length);}  可以看到创建了一个字符数组,长度是现有字符和连接字符的长度之和。然后,将它们的值复制到新的字符数组中。***,用这个字符数组创建一个String对象并返回。  所以这些操作很多,如果你计算一下,你会发现复杂度是O(n^2)。  为了解决这个问题,我们使用StringBuilder类。这就像可变的String类。拼接方法帮助我们避免不必要的重复。它的复杂度为O(n),远优于O(n^2)。  然而,Java8默认使用StringBuilder来连接字符串。  Java8文档解释:为了提高字符串拼接的性能,Java编译器在使用求值表达式时可以使用StringBuffer类或类似的技术来减少中间String对象的创建。  Java编译器处理这种情况:publicclassStringConcatenateDemo{publicstaticvoidmain(String[]args){Stringstr="Hello";海峡+=“世界”;}}上面的代码将编译成如下字节码:publicclassStringConcatenateDemo{publicStringConcatenateDemo();代码:0:aload_01:invokespecial#1//方法java/lang/Object."":()V4:returnpublicstaticvoidmain(java.lang.String[]);代码:0:ldc#2//StringHello2:astore_13:new#3//classjava/lang/StringBuilder6:dup7:invokespecial#4//Methodjava/lang/StringBuilder."":()V10:aload_111:invokevirtual#5//方法java/lang/StringBuilder.附加:(Ljava/lang/String;)Ljava/lang/StringBuilder;14:ldc#6//字符串世界16:invokevirtual#5//方法java/lang/StringBuilder.append:(Ljava/lang/String;)Ljava/lang/StringBuilder;19:invokevirtual#7//方法java/lang/StringBuilder.toString:()Ljava/lang/String;22:astore_123:return}  正如你在这些字节码中看到的那样,使用了StringBuilder因此我们不再需要在Java8中使用StringBuilder类。  英文原文:WeDon'tNeedStringBuilderforConcatenationAnyMore