字符串连接和 StringBuilders

可以使用+运算符执行字符串连接。例如:

String s1 = "a";
String s2 = "b";
String s3 = "c";
String s = s1 + s2 + s3; // abc

通常,编译器实现将使用涉及引擎盖下的 StringBuilder方法来执行上述串联。编译时,代码看起来类似于下面的代码:

StringBuilder sb = new StringBuilder("a");
String s = sb.append("b").append("c").toString();

StringBuilder 有几种重载方法可以追加不同类型,例如,附加 int 而不是 String。例如,实现可以转换:

String s1 = "a";
String s2 = "b";    
String s = s1 + s2 + 2; // ab2

以下内容:

StringBuilder sb = new StringBuilder("a");
String s = sb.append("b").append(2).toString();

上面的例子说明了一个简单的连接操作,它在代码中的一个地方有效地完成。串联涉及 StringBuilder 的单个实例。在某些情况下,连接是以累积方式执行的,例如循环:

String result = "";
for(int i = 0; i < array.length; i++) {
    result += extractElement(array[i]);
}
return result;

在这种情况下,通常不会应用编译器优化,每次迭代都会创建一个新的 StringBuilder 对象。这可以通过显式转换代码以使用单个 StringBuilder 来优化:

StringBuilder result = new StringBuilder();
for(int i = 0; i < array.length; i++) {
    result.append(extractElement(array[i]));
}
return result.toString();

StringBuilder 将初始化为只有 16 个字符的空白空间。如果你事先知道要构建更大的字符串,那么事先用足够的大小初始化它可能是有益的,这样内部缓冲区就不需要调整大小:

StringBuilder buf = new StringBuilder(30); // Default is 16 characters
buf.append("0123456789");
buf.append("0123456789"); // Would cause a reallocation of the internal buffer otherwise
String result = buf.toString(); // Produces a 20-chars copy of the string

如果要生成许多字符串,建议重用 StringBuilders:

StringBuilder buf = new StringBuilder(100);
for (int i = 0; i < 100; i++) {
    buf.setLength(0); // Empty buffer
    buf.append("This is line ").append(i).append('\n');
    outputfile.write(buf.toString());
}

如果(且仅当)多个线程正在写入同一缓冲区,请使用 StringBuffer ,这是 synchronizedsynchronized 版本。但是因为通常只有一个线程写入缓冲区,所以在没有同步的情况下使用 StringBuilder 通常会更快。

使用 concat() 方法:

String string1 = "Hello ";
String string2 = "world";
String string3 = string1.concat(string2);  // "Hello world"

这将返回一个新字符串,该字符串为 string1,并在末尾添加了 string2。你还可以将 concat() 方法与字符串文字一起使用,如下所示:

"My name is ".concat("Buyya");