日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程语言 > java >内容正文

java

Java StringBuilder神话被揭穿

發布時間:2023/12/3 java 34 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Java StringBuilder神话被揭穿 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

神話

用加號運算符連接兩個字符串是萬惡之源

-匿名Java開發人員

注意 :此處討論的測試的源代碼可以在Github上找到

從大學時代起,我就學會了使用+運算符將Java中的String連接視為致命的性能缺陷。 最近,在Backbase R&D上進行了一次內部審查,其中每當您使用plus運算符連接String時,由于在javac使用StringBuilder javac ,這種重復的口頭禪就被當作神話了。 我準備證明這一點并驗證不同環境下的現實。

考試

依靠編譯器優化String串聯意味著根據您采用的JDK供應商,情況可能會發生重大變化。 就我日常工作所需的平臺支持而言,應考慮三個主要供應商:

  • Oracle JDK
  • IBM JDK
  • ECJ-僅適用于開發人員

此外,盡管我們正式支持Java 5至6,但我們也正在考慮為我們的產品提供Java 7支持,在這三個供應商的基礎上增加了另外三層的間接。 為了 懶惰 為簡單起見, ecj編譯的字節碼將使用單個JDK(即Oracle JDK7)運行。 我準備了安裝了上述所有JDK的Virtualbox VM,然后開發了一些類來表示三種不同的串聯方法,根據特定的測試用例,每種方法調用總計三至四個串聯。 每個測試回合都運行測試類數千次,每個測試用例總共進行100回合。 相同的VM用于運行同一測試用例的所有回合,并跨不同的測試用例重新啟動,所有這些都使Java運行時能夠執行所有可能的優化,而不會以任何方式影響其他測試用例。 缺省選項用于啟動所有JVM。 可以在基準運行程序腳本中找到更多詳細信息。

編碼

Github上提供了測試用例和測試套件的完整代碼。 產生了以下不同的測試用例,以測量String串聯的性能差異,加上直接使用StringBuilder :

// String concat with plus String result = 'const1' + base; result = result + 'const2';// String concat with a StringBuilder new StringBuilder().append('const1').append(base).append('const2').append(append).toString(); }//String concat with an initialized StringBuilder new StringBuilder('const1').append(base).append('const2').append(append).toString();

一般的想法是在變量的常量String的開頭和結尾都提供一個串聯。 后兩種情況(兩者都顯式使用StringBuilder之間的區別在于后者使用1-arg構造函數,該構造函數使用結果的初始部分初始化構建器。

結果

足夠多的討論,您可以在下面查看生成的圖形,其中每個數據點對應一個測試回合(例如,同一測試類的1000次執行)。 隨后將討論結果以及更多細節。

討論

甲骨文JKD5顯然是輸家,與其他甲骨文相比似乎處于B聯賽。 但這實際上不是本練習的范圍,因此我們暫時將其忽略。 也就是說,我在上圖中觀察到了另外兩個有趣的地方。 首先是,使用加號運算符與使用顯式StringBuilder通常確實存在很大的差異, 尤其是如果您使用的Oracle Java5的執行樹時間比其他工作人員差的話。

第二個觀察結果是,雖然對于大多數JDK來說,顯式StringBuilder通常提供的速度是常規plus運算符的兩倍,但IBM JDK6似乎不會遭受任何性能損失,它總是平均需要25ms才能完成任務。所有測試用例。 仔細查看生成的字節碼會發現一些有趣的細節

字節碼

注意:反編譯類也可以在Github上使用。在所有可能的JDK中,即使存在加號, StringBuilders 始終用于實現String串聯。 而且,在所有廠商和版本中,同一測試用例幾乎沒有任何區別 。 唯一的區別是ecj ,這是唯一巧妙地優化CatPlus測試用例以調用StringBuilder的1-arg構造函數而不是0-arg版本的方法。

比較生成的字節碼可以揭示在不同場景下可能影響性能的因素:

  • 與plus串聯時,只要發生串聯,就會創建StringBuilder新實例 。 由于構造函數的無用調用,這很容易導致性能下降,并且由于丟棄實例而給垃圾收集器帶來更多壓力
  • 如果且僅當您在原始代碼中以這種方式編寫StringBuilder ,編譯器才會照搬您,并且僅使用String的1-arg構造函數來初始化StringBuilder 。 這分別導致對CatSB和CatSB2的StringBuilder.append四個和三個調用。

結論

字節碼分析為原始問題提供了最終答案。 您是否需要顯式使用StringBuilder來提高性能? 是上面的圖清楚地表明,除非使用IBM JDK6運行時,否則在使用plus運算符時,您將損失50%的性能,盡管在顯式StringBuilder時,它在候選對象上的表現會稍差一些。 同樣,看到JIT優化如何影響整體性能也很有趣:例如,即使在兩個顯式StringBuilder測試用例之間存在不同的字節碼,從長遠來看,最終結果也絕對相同。


參考: Java StringBuilder神話從我們的JCG合作伙伴 Carlo Sciolla在Skuro博客中揭穿 。

翻譯自: https://www.javacodegeeks.com/2013/03/java-stringbuilder-myth-debunked.html

總結

以上是生活随笔為你收集整理的Java StringBuilder神话被揭穿的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。