本文着重介紹下,應該在何時恰當的使用string,stringbuffer,stringbuilder。
1,執行速度
StringBuilder > StringBuffer > String
我們知道String是字符串常量,不可變對象,因此每次對String進行操作的時候實際上是生成了一個新的String對象,然后將指針指向新的String對象上,之前的String對象就沒有了指針引用,當內存中無引用的對象多了之后,就會觸發JVM的GC操作了。
StringBuilder和StringBuffer是字符串變量,因此當我們對字符串做操作的時候,實際上都是操作的同一個對象,不會創建新的對象。
注意:
String str="hel"+"lo"; String a = "hel"; String b ="lo"; String c = a+b;
上面的兩部分代碼雖然輸出的結果都是“hello”,但是在jvm中的內存分布是完全不同的。
String str="hel"+"lo"; 中的str是一個編譯時常量,最后分配到內存里面的只有"hello" 這一款內存區域。
而下面的三行代碼,則需要在內存中分配三塊地址,【"hel","lo","hello"】。
由此可以得出執行順序了,但是StringBuilder為什么會比StringBuffer快呢,請繼續往下看
2,線程安全
StringBuilder是線程不安全的,而StringBuffer是線程安全的
StringBuffer 上的主要操作是 append 和 insert 方法,可重載這些方法,以接受任意類型的數據。每個方法都能有效地將給定的數據轉換成字符串,然后將該字符串的字符追加或插入到字符串緩沖區中。append 方法始終將這些字符添加到緩沖區的末端;而 insert 方法則在指定的點添加字符。
例如,如果 z 引用一個當前內容是“start”的字符串緩沖區對象,則此方法調用 z.append("le") 會使字符串緩沖區包含“startle”,而 z.insert(4, "le") 將更改字符串緩沖區,使之包含“starlet”。
java.lang.StringBuilder一個可變的字符序列是5.0新增的。此類提供一個與 StringBuffer 兼容的 API,但不保證同步。該類被設計用作 StringBuffer 的一個簡易替換,用在字符串緩沖區被單個線程使用的時候(這種情況很普遍)。如果可能,建議優先采用該類,因為在大多數實現中,它比 StringBuffer 要快。兩者的方法基本相同。
如果一個StringBuffer對象在字符串緩沖區被多個線程使用時,StringBuffer中很多方法可以帶有synchronized關鍵字,所以可以保證線程是安全的,但StringBuilder的方法則沒有該關鍵字,所以不能保證線程安全,有可能會出現一些錯誤的操作。所以如果要進行的操作是多線程的,那么就要使用StringBuffer,但是在單線程的情況下,還是建議使用速度比較快的StringBuilder。
3,總結
String:適用於少量的字符串操作的情況
StringBuilder:適用於單線程下在字符緩沖區進行大量操作的情況
StringBuffer:適用多線程下在字符緩沖區進行大量操作的情況