| 特性 | String | StringBuffer | StringBuilder |
|---|---|---|---|
| 可變性 | 不可變 | 可變 | 可變 |
| 線程安全 | 不可變天然安全 | 同步方法,安全 | 非同步,不安全 |
| 性能 | 頻繁修改極差 | 中等(同步開銷) | 最高(無同步) |
| JDK 版本 | 1.0+ | 1.0+ | 5.0+ |
| 繼承關係 | final class | AbstractStringBuilder 子類 | AbstractStringBuilder 子類 |
String s1 = "abc";
for (int i = 0; i < 10000; i++) {
s1 += "def"; // 每次創建新 String、新 char[]、複製內容
s1 = "abc"; // 重置,但 10000 個臨時對象已產生
}
循環結束後堆中殘留大量垃圾對象,觸發頻繁 GC,嚴重影響吞吐量。
// 情況 1:字面量拼接 → 編譯期常量折疊
String s1 = "This is only a" + " simple" + " test";
// 字節碼等價於:String s1 = "This is only a simple test"; // 極快
// 情況 2:變量拼接 → 運行時 StringBuilder
String s2 = "This is only a";
String s3 = " simple";
String s4 = " test";
String s5 = s2 + s3 + s4;
// 字節碼:new StringBuilder().append(s2).append(s3).append(s4).toString() // 較慢
| 操作類型 | 耗時 (ms) |
|---|---|
| String += 拼接 | 4,392 |
| StringBuffer.append() | 0 |
| StringBuilder.append() | 0 |
| 變量引用拼接 | 15 |
| 字面量直接拼接 | 0 |
| 類型 | 耗時 (ms) |
|---|---|
| StringBuffer | 265 |
| StringBuilder | 219 |
結論:StringBuilder 約快 15-20%,穩定優於 StringBuffer。
// StringBuffer 核心方法
public synchronized int length() { return count; }
public synchronized StringBuffer append(String str) {
toStringCache = null;
super.append(str);
return this;
}
// StringBuilder 核心方法(無 synchronized)
public int length() { return count; }
public StringBuilder append(String str) {
super.append(str);
return this;
}
兩者共享 AbstractStringBuilder 實現,差異僅在公共方法同步修飾符。
StringBuilder(首選)StringBuffer 或 ThreadLocalString 直連(編譯器優化)log.debug("user={}", user) 避免不必要拼接
// 預估最終長度,避免多次擴容(默認 16,擴容 2倍+2)
StringBuilder sb = new StringBuilder(256);
for (int i = 0; i < 100; i++) sb.append("item").append(i);
擴容涉及數組複製,預分配可顯著提升大量拼接性能。