LeakCanary是一個內存泄漏檢測庫,它可以在我們的應用發生內存泄漏的時候發出提醒,提醒包括通知和Log。GitHub
這個庫使用起來比較簡單:
①添加依賴:
1 dependencies { 2 debugCompile 'com.squareup.leakcanary:leakcanary-android:1.5' 3 releaseCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5' 4 testCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5' 5 }
②自定義Application
1 public class MyApplication extends Application { 2 @Override 3 public void onCreate() { 4 super.onCreate(); 5 if (LeakCanary.isInAnalyzerProcess(this)) { 6 return; 7 } 8 LeakCanary.install(this); 9 } 10 }
這樣就可以了。
我們這里通過簡單的例子看看它的效果,我們都知道,內存泄漏比較容易發生的,就是因為生命周期不匹配導致的。Android中的組件都是有特定生命周期的,而當這些組件中存在着不可釋放的變量時,組件的生命周期便會出現異常,導致無法被GC釋放。
這里舉一個簡單的例子:
1 public class SecondActivity extends AppCompatActivity { 2 static Demo sDemo; 3 4 @Override 5 protected void onCreate(Bundle savedInstanceState) { 6 super.onCreate(savedInstanceState); 7 setContentView(R.layout.activity_second); 8 if (sDemo == null) { 9 sDemo = new Demo(); 10 } 11 finish(); 12 } 13 14 class Demo { 15 } 16 17 }
這個Activity中,存在一個靜態的Demo實例,並且這個實例在Activity初始化的時候也進行了初始化,接着我們在初始化完畢后finish掉這個Activity。
因為sDemo是一個靜態的變量並且不為null,所以GC不會將其清理,而Activity因為持有這個靜態變量,生命周期也不能正常執行,這樣這個Activity就被泄漏了。
我們在MainActivity中打開這個Activity,啟動應用。
模擬器的狀態欄會出現一個圖標,我們打開可以得到如下界面:
可以看到,和我們分析的一樣,SecondActivity的實例被泄漏了。
實際上,LeakCanary除了會在界面中顯示泄漏信息之外,Log中也一樣會輸出泄漏的具體信息:
這樣追蹤泄漏的地方就不難了。