再一次在字符串附加vs concat vs +

可能是我分裂头发,但我想知道以下情况:

String newString = a + b + c; //case 1 String newString = a.concat(b).concat(c); //case 2 StringBuilder newString = new StringBuilder(); //case 3 newString.append(a); newString.append(b); newString.append(c); 

哪个最好用?

我最好的意思是任何方式

阅读这些,其他post说案例3不是最佳表现明智,其他案例1最终将在案例3等。

更具体。

例如,将所有设置放在一边,如果你不得不维护他的代码,哪种风格更适合从另一个程序员那里看到它?

或者您认为哪种编程效率更高?
或者你会认为更快等等。

我不知道怎么表达这个。

像案例3这样的答案可能会更快,但绝大多数程序员更喜欢案例1,因为如果它在某种程度上得到了很好的阐述,它也是最可读的

案例1简洁明了,表达了意图,相当于案例3。

案例2的效率较低,而且可读性较差。

案例3几乎与案例1一样有效,但更长,更不易读。

使用案例3只有在必须在循环中连接时才能使用。 否则,编译器将情况1编译为情况3(除了它使用new StringBuilder(a)构造StringBuilder),这使得它比你的情况3)更有效。

案例3是性能最高的forms,但JVM将案例1转换为案例3。

但我认为案例2是最差的,它不像案例1那样可读,而不像案例3那样可行。

如果你想在循环中连接字符串只是用例3,你可以很容易地测试性能增益,但如果它不在循环中(或者你没有在序列中附加大量字符串)它们几乎是相同的。

你不应该使用+运算符的情况是:

 String a = ""; for (String x : theStrings) { a += x; } 

要么

 String a = b + c; a = a + d; a = a + e; a = a + f; 

案例3在大多数方面都更好。 在案例3中,您不会最终创建3个字符串对象。 由于字符串不变性,2将为每个+(或)concat创建字符串对象的开销。

编辑:重新阅读文档并同意大多数评论,案例1是案例3。

对于简单的情况,使用+显然更具可读性。

对于罕见的更复杂的情况, StringBuilder是有道理的。 如果你在分割线条,那么+很快就会成为性能阻力。 循环从O(n)性能变为O(n ^ 2) – 如果n很小则不是问题,但是如果n在笨拙的情况下可能很大(可能是在做一些关键的事情,或者当某人是恶意的时候),这是一个大问题。

与其他答案相反,如果你只有三个琴弦,那么concat可能是表演冠军。 我是精神病吗? 不。考虑其他两个选项。 您正在创建一个带有数组的StringBuilder对象。 附加字符串可能需要更换数组,并且您可能在数组的末尾留下奇数位(这是分配的特定粒度,因此一些额外的char可能会或可能不会增加内存使用量)。 如果您讨厌阅读代码的每个人,您可以计算必要的容量。 最好的情况,两个数组(一个用于StringBuilder ,一个用于String (过去八年没有共享))每个结果文本的大小和另外两个对象( StringBuilderString )。 现在,对于concat您将分配给具有两个数组的String对象,但第一个数组将是c.length()更短。 这是一场胜利! 好吧,不是为了可读性。

免责声明:JVM可以进行疯狂优化,包括转义分析后的堆栈分配和核心类的特殊大小写。 与手工混淆的代码相比,它们更有可能优化常见和简单的代码。

在使用JDK 1.8进行性能分析时,我发现案例2在性能方面是赢家。

 class Solution { public static void main(String[] args) { String s ="ABC", s1 = "", s2 = "", s3 = ""; long t1 = System.nanoTime(); for(int i = 1; i < 11; i++) { s1 = s1 + s; } System.out.println(System.nanoTime() - t1); System.out.println(s1); long t2 = System.nanoTime(); for(int i = 1; i < 11; i++) { s2 = s2.concat(s); } System.out.println(System.nanoTime() - t2); System.out.println(s2); long t3 = System.nanoTime(); StringBuilder sb = new StringBuilder(); for(int i = 1; i < 11; i++) { sb.append(s); } s3 = sb.toString(); System.out.println(System.nanoTime() - t3); System.out.println(s3); } } 

结果:

40615

ABCABCABCABCABCABCABCABCABCABC

9157

ABCABCABCABCABCABCABCABCABCABC

20243

ABCABCABCABCABCABCABCABCABCABC