1. 程式人生 > >Android studio記憶體洩露分析工具使用

Android studio記憶體洩露分析工具使用

什麼是記憶體洩漏

Android虛擬機器的垃圾回收採用的是根搜尋演算法。GC會從根節點(GC Roots)開始對heap進行遍歷。到最後,部分沒有直接或者間接引用到GC Roots的就是需要回收的垃圾,會被GC回收掉。而記憶體洩漏出現的原因就是存在了無效的引用,導致本來需要被GC的物件沒有被回收掉。
比如下面這個常見的程式碼:

public class Singleton {
    private static Singleton instance;
    private Context mContext;
    private Singleton(Context context){
        this
.mContext = context; } public static Singleton getInstance(Context context){ if (instance == null){ synchronized (Singleton.class){ if (instance == null){ instance = new Singleton(context); } } } return
instance; } }

由於在呼叫Singleton的getInstance()時傳入了Activity,當instance沒有釋放時,這個Activity會一直存在從而導致記憶體出現洩露。

正確的方式:將new Singleton(context)改為new Singleton(context.getApplicationContext()),這樣便和傳入的Activity沒關係了。
在實際開發過程中,記憶體洩露並不是那麼容易找到起因,因此就需要用到一些工具來輔助找到問題所在。

檢測記憶體洩露的發生

在android stdio中執行程式,找到Android Monitor顯示如下介面,並重點關注Memory這一項,用以觀察不同時間App中記憶體的動態使用情況:
這裡寫圖片描述

分析步驟

  1. 程式執行起來後,點選橙色小車車這裡寫圖片描述 手動觸發一次GC,點選dump java heap 這裡寫圖片描述成功後會自動開啟 hprof檔案,檔案以Snapshot+時間來命名,通過它可檢視Java的Heap。Reference Tree代表指向該例項的引用,可以從這裡面檢視記憶體洩漏的原因,Shallow Size(淺堆大小)指的是該物件本身佔用記憶體的大小,Retained Size(保留堆大小)代表該物件被釋放後,垃圾回收器能回收的記憶體總和。
    這裡寫圖片描述

2.接下來分析記憶體洩露可以有兩種方式:
1)在上訴Android Studio自帶的介面中分析便好。點選介面中的Analyzer Tasks,檢視介面中的Analyzer Results 處是否有結果。看網上的這張圖便一目瞭然。
這裡寫圖片描述
在Reference Tree裡面,直接就可以看到持有該Activity的單例物件,直接定位到該單例中的程式碼,發現程式碼中出現了
public static VideoTagHelper getInstance(Context context) {
if (tagHelper == null) {
tagHelper = new VideoTagHelper();
}
tagHelper.context = context;
return tagHelper;
}
在修復了記憶體洩漏問題後,網友舉例的程式碼中記憶體使用下降了16.3%!!!
2)通過Android Studio自帶的介面,檢視記憶體洩露還不是很智慧,可以藉助第三方工具,比如MAT。Eclipse Memory Analyze 是Java 堆轉儲檔案分析工具,可以幫助你發現記憶體漏洞和減少記憶體消耗。下載地址 http://eclipse.org/mat/downloads.php 。開啟它。
這裡寫圖片描述
注意:MAT並不會準確地告訴我們哪裡發生了記憶體洩漏,而是會提供一大堆的資料和線索,我們需要自己去分析這些資料來去判斷到底是不是真的發生了記憶體洩漏。
用MAT開啟記憶體分析的檔案: Android Studio生成的hprof檔案在Android Studio的Captrues這個目錄中可以找到,使用MAT直接開啟它是行不通的,會出現下面錯誤
這裡寫圖片描述
因為android的虛擬機器匯出的記憶體檔案hprof檔案格式與標準的 java hprof檔案格式標準不一樣,根本原因是兩者的虛擬機器不一致導致的。因此需要將它做個轉換。找到android sdk的目錄執行cmd,
這裡寫圖片描述
開啟命令列視窗後,執行指令hprof-conv 原始檔 目標檔案將檔案進行轉換才能在MAT中成功開啟。
使用MAT分析
1)開啟標準的hprof檔案後,可以看到
這裡寫圖片描述
點選Leak Suspects 連結可以生成報告
2)通過上面那張圖,對記憶體狀態有一個整體印象,接著找到有可能導致記憶體洩露的元凶,通常也就是消耗記憶體最多的物件,再進一步去檢視這個記憶體消耗大戶的具體情況,看看是否有什麼異常的行為。
可以通過檢視從 GC 根元素到記憶體消耗聚集點的最短路徑。
這裡寫圖片描述
點選detail來到每個problem,具體問題具體分析。直到找到問題。
這裡寫圖片描述