1.簡介
你們可能會想到使用mat,但是效率不是很高,對於乙個記憶體洩漏問題,可能要進行多次排查和對比才能找到問題原因。
所以我推薦你們用square公司基於mat開源的leakcanary
2.提示方式
3.如何使用
dependencies
//第一種檢測到某個activity 有記憶體洩露,leakcanary 就會給出提示。
public
class
extends
leakcanary.
install
(this);
}}//第二種其他類的記憶體洩漏,這時我們就需要使用refwatcher來進行監控。
public
class
extends
private refwatcher setupleakcanary()
return leakcanary.
install
(this);
}public
static refwatcher getrefwatcher
(context context)
}
2.3舉例,我們在一段存在記憶體洩漏的**中引入leakcanary監控
public
class
otheractivity
extends
class
leakthread
extends
thread
catch
(interruptedexception e)}}
@override
protected
void
ondestroy()
}
2.4原因
otheractivity存在記憶體洩漏,原因就是非靜態內部類leakthread持有外部類otheractivity的引用,leakthread中做了耗時操作,導致otheractivity無法被釋放。
4.注意
4.1 如果想要監控fragment,在fragment中新增如上的ondestroy方法是有用的。
在對應fragment頁面中ondestroy中加入
getrefwatcher
(this);
refwatcher.
watch
(this);
4.3因為leakcanary需要生成hprof檔案
請在清單檔案androidmanifest.xml中新增許可權
<
!– sdcard中建立與刪除檔案許可權 –>
"android.permission.mount_unmount_filesystems"
/>
<
!– 向sdcard寫入資料許可權 –>
"android.permission.write_external_storage"
/>
5.原理
5.1觸發檢測
每次當activity/fragment執行完ondestroy生命週期,leakcanary就會獲取到這個activity/fragment,然後初始化refwatcher對它進行分析,檢視是否存在記憶體洩漏。
5.2判斷是否存在記憶體洩漏
首先嘗試著從referencequeue佇列中獲取待分析物件,如果不為空,那麼說明正在被系統**,如果直接就返回done,說明已經被系統**了,如果沒有被系統**,可能存在記憶體洩漏,手動觸發系統gc,然後再嘗試移除待分析物件,如果還存在,說明存在記憶體洩漏。
5.3 分析記憶體洩漏
確定有記憶體洩漏後,呼叫heapdumper.dumpheap()生成.hprof檔案目錄。haha 是乙個由 square 開源的 android 堆分析庫,分析 hprof 檔案生成snapshot物件。snapshot用以查詢物件的最短引用鏈。找到最短引用鏈後,定位問題,排查**將會事半功倍。
整體流程如下
6.總結
leakcanary對於記憶體洩漏的檢測非常有效,但也並不是所有的記憶體洩漏都能檢測出來。
6.1無法檢測出service中的記憶體洩漏問題
6.2如果最底層的mainactivity一直未走ondestroy生命週期(它在activity棧的最底層),無法檢測出它的呼叫棧的記憶體洩漏。
所以說leakcanary針對activity/fragment的記憶體洩漏檢測非常好用,但是對於以上檢測不到的情況,還得配合android monitor + mat 來分析。
我該怎麼辦!
今天是我比較難受的一天,發現有些事情不到最後是不知什麼結局,或許你的一萬種猜想沒有一種實現,哎,作業雖然交了,但我還是心裡難受,我懂得了很多,不應對別人抱太大希望,應該自己去努力,不論結果怎麼樣但心裡是甜的,不堅持到最後一刻,或許成功還是不屬於你,就像我們副部,何苦堅持那麼久,幹了那麼多事,挨罵也接...
我該怎麼辦
想了好久,不知道該怎麼辦,家裡情況這個樣子,如今真的不知道是去是留。父親癱瘓在床,母親有些神經不正常,我應該是去上學還是留下來照顧他們。說實話,我一點都不想留下來,我沒有這個毅力,沒有一直照顧父親的毅力,也許時間長了我會厭煩,不知道說出這種話是不是算很不孝,1月份我在醫院的時候就是一直呆在了父親身邊...
記憶體耗盡怎麼辦?
如果在申請動態記憶體時找不到足夠大的記憶體塊,malloc和new將返回null指標,宣告記憶體申請失敗。通常有三種方式處理 記憶體耗盡 問題。1 判斷指標是否為null,如果是則馬上用return語句終止本函式。例如 void func void 2 判斷指標是否為null,如果是則馬上用exit...