java性能優化1--字元串優化處理

来源:http://www.cnblogs.com/dqqiu/archive/2016/07/09/5656444.html
-Advertisement-
Play Games

以上代碼中,s1和s2引用的是相同的地址,故而第四行列印出的結果是true;而s3雖然只與s1,s2相等,但是s3時通過new String("123")創建的,重新開闢了記憶體空間,因引用的地址不同,所以第5行列印出false;intern方法返回的是String對象在常亮池中的引用,所以最後一行打 ...


  1. String對象
      String對象是java中重要的數據類型,在大部分情況下我們都會用到String對象。其實在Java語言中,其設計者也對String做了大量的優化工作,這些也是String對象的特點,它們就是:不變性常量池優化String類的final定義

    1.1 不變性
      String對象的狀態在其被創建之後就不在發生變化。為什麼說這點也是Java設計者所做的優化,在java模式中,有一種模式叫不變模式,瞭解的童鞋也應該知道不變模式的作用:在一個對象被多線程共用,而且被頻繁的訪問時,可以省略同步和鎖的時間,從而提高性能。而String的不變性,可泛化為不變模式。

    1.2 常量池優化

      常量池優化指的是什麼呢?那就是當兩個String對象擁有同一個值的時候,他們都只是引用了常量池中的同一個拷貝。所以當程式中某個字元串頻繁出現時,這個優化技術就可以節省大幅度的記憶體空間了。例如:

    1 String s1  = "123";
    2 String s2  = "123";
    3 String s3 = new String("123");
    4 System.out.println(s1==s2);      //true
    5 System.out.println(s1==s3);      //false
    6 System.out.println(s1==s3.intern());    //true

      以上代碼中,s1和s2引用的是相同的地址,故而第四行列印出的結果是true;而s3雖然只與s1,s2相等,但是s3時通過new String("123")創建的,重新開闢了記憶體空間,因引用的地址不同,所以第5行列印出false;intern方法返回的是String對象在常亮池中的引用,所以最後一行列印出true。


    1.3 final的定義
      String類以final進行了修飾,在系統中就不可能有String的子類,這一點也是出於對系統安全性的考慮。

  2. 字元串操作中的常見優化方法
    2.1 split()方法優化
      通常情況下,split()方法帶給我們很大的方便,但是其性能不是很好。建議結合使用indexOf()和subString()方法進行自定義拆分,這樣性能會有顯著的提高。    

    2.2 String常亮的累加操作優化方法
      示例代碼:

     1 String s = "";
     2 long sBeginTime = System.currentTimeMillis();
     3 for (int i = 0; i < 100000; i++) {
     4     s+="s";
     5 }
     6 long sEndTime = System.currentTimeMillis();
     7 System.out.println("s拼接100000遍s耗時: " + (sEndTime - sBeginTime) + "ms");
     8         
     9 StringBuffer s1 = new StringBuffer();
    10 long s1BeginTime = System.currentTimeMillis();
    11 for (int i = 0; i < 100000; i++) {
    12     s1.append("s");
    13 }
    14 long s1EndTime = System.currentTimeMillis();
    15 System.out.println("s1拼接100000遍s耗時: " + (s1EndTime - s1BeginTime) + "ms");
    16         
    17 StringBuilder s2 = new StringBuilder();
    18 long s2BeginTime = System.currentTimeMillis();
    19 for (int i = 0; i < 100000; i++) {
    20     s2.append("s");
    21 }
    22 long s2EndTime = System.currentTimeMillis();
    23 System.out.println("s2拼接100000遍s耗時: " + (s2EndTime - s2BeginTime) + "ms");

      結果:

      

      上例所示,使用+號拼接字元串,其效率明顯較低,而使用StringBuffer和StringBuilder的append()方法進行拼接,效率是使用+號拼接方式的百倍甚至千倍,而StringBuffer的效率比StringBuilder低些,這是由於StringBuffer實現了線程安全,效率較低也是不可避免的。所以在字元串的累加操作中,建議結合線程問題選擇,應避免使用+號拼接字元串。

    2.3 StringBuffer和StringBuilder的選擇
      上例中也使用過StringBuffer和StringBuilder了,兩者只有線程安全方面的差別,所以呢,在無需考慮線程安全的情況下,建議使用性能相對較高的StringBuilder類,若系統要求線程安全,就選擇StringBuffer類。

    2.4 基本數據類型轉化為String類型的優化方案
      示例代碼:
      

     1 Integer num  = 0;
     2 int loop = 100000;  // 將結果放大100000倍,以便於觀察結果
     3 long beginTime = System.currentTimeMillis();
     4 for (int i = 0; i < loop; i++) {
     5     String s = num+"";
     6 }
     7 long endTime = System.currentTimeMillis();
     8 System.out.println("+\"\"的方式耗時: " + (endTime - beginTime) + "ms");
     9         
    10         
    11 beginTime = System.currentTimeMillis();
    12 for (int i = 0; i < loop; i++) {
    13     String s = String.valueOf(num);
    14 }
    15 endTime = System.currentTimeMillis();
    16 System.out.println("String.valueOf()的方式耗時: " + (endTime - beginTime) + "ms");
    17         
    18 beginTime = System.currentTimeMillis();
    19 for (int i = 0; i < loop; i++) {
    20     String s = num.toString();
    21 }
    22 endTime = System.currentTimeMillis();
    23 System.out.println("toString()的方式耗時: " + (endTime - beginTime) + "ms");

      以上示例中,String.valueOf()直接調用了底層的Integer.toString()方法,不過其中會先判空;+""由StringBuilder實現,先調用了append()方法,然後調用了toString()方法獲取字元串;num.toString()直接調用了Integer.toString()方法,所以效率是:num.toString()方法最快,其次是String.valueOf(num),最後是num+""的方式。以下是結果截圖:
      

      建議童鞋們避免使用+""的方式轉換,最好是使用基本數據類型自帶的toString()方法轉換。就先分享到這兒吧!!!


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 表單重覆提交是在多用戶Web應用中最常見、帶來很多麻煩的一個問題。有很多的應用場景都會遇到重覆提交問題,比如: 點擊提交按鈕兩次。 點擊刷新按鈕。 使用瀏覽器後退按鈕重覆之前的操作,導致重覆提交表單。 使用瀏覽器歷史記錄重覆提交表單。 瀏覽器重覆的HTTP請求。 幾種防止表單重覆提交的方法 禁掉提交 ...
  • public class SuperClass{ public void printA(){ System.out.print("SuperClass-printA"); printB(); } public void printB(){ System.out.print("SuperClass-p ...
  • 最近打算寫個簡單的配置中心,考慮到實現便捷性,語言選擇了go,由於其中計劃用到zk,就調研了下golang的zk客戶端,並實現了個簡單的分散式server。 ...
  • ...
  • * 1、繼承自抽象類 AbstractSet,實現介面 Set、Cloneable、Serializable; * 2、元素無順序; * 3、元素不可重覆; * 4、採用哈希演算法插入數據,插入速度快; * 5、非線程安全,輕量級; * 6、由於實現了介面 Cloneable,故此可以被覆制; * 7 ...
  • 按照一般的學習慣例,第一個程式自然就是"Hello World"。 運行結果如上圖。代碼: 在主函數中只需4句話即可創建一個新的視窗,併在其中顯示文字。 第1~2行:包含頭文件。 在Qt中,每一個類都有一個與該類同名的頭文件。 例如主函數中的QApplication類,它的頭文件就是,QLabel類... ...
  • 好久沒有寫博文了,寫個簡單的東西熱熱身,分享給大家。 jdbc相信大家都不陌生,只要是個搞java的,最初接觸j2ee的時候都是要學習這麼個東西的,誰叫程式得和資料庫打交道呢!而jdbc就是和資料庫打交道非常基礎的一個知識,也是比較接近底層的,在實際的工作中大家用得更多的其實還是比較成熟的框架,例如 ...
  • 1.包 package pack; /*定義包,放在程式的第一行,包名所以字母小寫*/class PackageDemo{ public static void main(String[] args) { packa.DemoA a=new packa.DemoA(); /*編譯時將會出現兩個錯誤, ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...