2012-06-20 68 views
4

我的android應用程序隨着時間的推移會佔用越來越多的內存。我拿了堆轉儲並用MAT分析。我的android應用程序消耗太多內存

這裏的主要泄漏嫌疑人:

所以好像從內存中後,我退出應用程序也不會被清除我的活動之一(與返回鍵),然後當我重新啓動應用程序創建一個新的實例並填充內存。

現在,如果他們是PhantomReferences爲什麼內存不清除一段時間後,或者當我退出應用程序?即使當我使用其他應用程序等時,內存也不會被清除。完全關閉應用程序的唯一方法是使用任務管理器手動終止應用程序。

我該怎麼做才能避免這種無政府狀態的內存消耗?

編輯:

我發現了問題! 每個活動都使用Thread.setDefaultUncaughtExceptionHandler()設置CustomExceptionHandler,並且該CustomExceptionHandler保持對上下文的引用。所以我擺脫了上下文引用,並且在'onDestroy()'方法中'取消了'DefaultUncaughtExceptionHandler。現在真的好多了!

+0

你有線程,Asyntasks ...? – Jonas

+0

是的確都是 – Alexis

+1

......你殺了他們嗎? – Jonas

回答

5

我會使用MAT的支配樹功能來找出上面那些引用是什麼,這可能會讓你知道哪個是Activity是罪魁禍首。

請確保你沒有通過任何地方的Context並持有對它的引用,這是一個經典的android內存泄漏,它確實很容易!

儘管一些靜態分析工具皺眉這一點,在你的Activity可以null所有本地變量(除原語),它有助於有時輕推垃圾收集器,可以使一個更容易分析堆轉儲的onDestroy()方法在MAT。

+0

我猜想當方法退出時,局部變量會自動從堆棧中取出。你的意思是實例變量應該在onDestroy()方法中標記爲null?我有點不清楚。 – Manpreet

5

一些通用的方法,以減少應用程序的大小我一般遵循的是這樣的:

  • 呼叫完成()下面通過一個Intent到下一個活動,這將避免堆砌堆棧和GC幫助(垃圾回收)
  • 如果您不使用共享首選項來保存數據,請在退出時通過調用System.exit()來刷新它們()
  • 如果您發現任何可用的圖像/佈局xml/java類最終計劃,確保您將其從項目中移除
  • 由於JPEG圖像佔用大量內存,因此圖像必須爲.png。
  • 在使用數據庫(sqlite,內部數據庫等)的情況下,更好的方法是使用「try/catch/finally」塊。在嘗試打開數據庫,最後關閉它,這將避免造成內存泄漏因爲不關閉遊標或數據庫。
  • 使用AsyncTask代替線程。在onPostExecute()函數中,關閉進度對話框(如果有的話)。