字符串连接操作符(+)是把多个字符串合并为一个字符串的便利途径。要想产生单独一行的输出,或者构造一个字符串来表示一个较小的、大小固定的对象,使用连接操作符是非常合适的,但是它不适合运用在大规模的场景中。为连接n个字符串而重复地使用字符串连接操作符,需要n的平方级的时间。这是由于字符串不可变而导致的不幸结果。当两个字符串被连接在一起时,他们的内容都要被拷贝。
例如:考虑下面的方法,它通过反复连接每个项目行,构造出一个代表该对账单的字符串。代码如下:
public String statement(){
String result = "";
for (int i = 0; i < numItems; i++ ){
result += lineForItem(i);
return result;
}
}
如果项目数量巨大,这个方法的执行时间就难以估算。为了获得可以接受的性能,请使用StringBuffer替代String,来存储建筑中的对账单。
public String statement(){
StringBuffer sb = new StringBuffer(numItems() * LINE_WIDTH);
for (int i = 0; i < numItems(); i++ ){
sb.append(lineForItem(i));
}
return sb.toString();
}
上诉两种做法的性能差别非常大。如果numItems返回100,并且lineForItem返回一个固定长度为80的字符串,在作者的机器上,第二种做法比第一种做法要快85倍(书上的例子用的是StringBuilder)。因为第一种做法的开销随项目数量而呈平方级增加,所以,项目数越大,性能的差别会越显著。
long start = System.currentTimeMillis();
String string = "aa";
for (int i = 0; i < 100000; i++) {
string += "a";
}
long end = System.currentTimeMillis();
System.out.println(end - start);
long start1 = System.currentTimeMillis();
StringBuilder sb = new StringBuilder("aa");
for (int i = 0; i < 100000; i++) {
sb.append("a");
}
long end1 = System.currentTimeMillis();
System.out.println(end1 - start1);
输出结果:
5110
4
操作的数量越多 ,差距就越明显
总结:不要使用字符串连接操作符来合并多个字符串,除非性能无关紧要。相反,应该使用StringBuffer的append方法。