簡體   English   中英

如何衡量Android應用數據大小並識別存儲泄漏?

[英]How to measure Android app data size and identify storage leaks?

我制作了一個小型Android應用程序並且已經使用了一段時間了。 我注意到,在設置中,我應用程序特征的“數據”行(我對分析“應用程序”行和“緩存”行上顯示的數量不感興趣),它顯示大約20 MB,其中對我來說似乎很重要。 我擔心應用程序存在泄漏(即它產生的數據永遠不會被刪除)。

我決定調查和衡量可能占用那么多空間的東西。 我幾乎使用了這個應用程序的所有可用存儲選項 :SQLite DB,內部文件,外部文件,共享首選項(以及包括Glide圖片加載的緩存文件)。

到目前為止,由於有關SQLite DB的問題 ,我發現我的DB文件大約需要500 kB。 我通過遞歸掃描文件和文件夾getFilesDir()了我在內部和app私有外部文件中使用10 kB數據。 我還沒有分析共享首選項大小,但我存儲少於20個鍵/值對。

探索文件夾getCacheDirs()我還發現Glide使用大約3 MB的緩存(接近Android設置應用程序所說的)。

我的問題是,哪些導致我錯過了找到這個19.5 MB的數據我找不到的位置? 我忘記了某種可能占用空間的存儲空間嗎? 而且,更一般地說,是否有工具來分析存儲泄漏(即應用程序產生的數據可能永遠不會被刪除)?

按照@James的建議,我開始探索不同的文件夾,在與同事討論問題並嘗試探索許多文件夾后,我終於發現大部分數據來自我以前的Webview的緩存。 我發布了所有的調查,希望它會有所幫助。

當應用程序啟動時,我執行了以下代碼,從我的主要活動中調用analyseStorage(this)

public void analyseStorage(Context context) {
  File appBaseFolder = context.getFilesDir().getParentFile();
  long totalSize = browseFiles(appBaseFolder);
  Log.d(STORAGE_TAG, "App uses " + totalSize + " total bytes");
}

private long browseFiles(File dir) {
  long dirSize = 0;
  for (File f: dir.listFiles()) {
    dirSize += f.length();
    Log.d(STORAGE_TAG, dir.getAbsolutePath() + "/" + f.getName() + " uses " + f.length() + " bytes");
    if (f.isDirectory()) {
      dirSize += browseFiles(f);
    }
  }
  Log.d(STORAGE_TAG, dir.getAbsolutePath() + " uses " + dirSize + " bytes");
  return dirSize;
}

重要的是要專門掃描context.getFilesDir().getParentFile() ,它匹配文件夾/data/data/my.app.package/

執行該代碼后,我有以下日志:

D/storage﹕ /data/data/my.app.package/lib uses 0 bytes
D/storage﹕ /data/data/my.app.package/cache uses 3371773 bytes
D/storage﹕ /data/data/my.app.package/databases uses 483960 bytes
D/storage﹕ /data/data/my.app.package/shared_prefs uses 604 bytes
D/storage﹕ /data/data/my.app.package/app_webview uses 9139469 bytes
D/storage﹕ /data/data/my.app.package/files uses 7723 bytes
D/storage﹕ /data/data/my.app.package/app_ACRA-approved uses 0 bytes
D/storage﹕ /data/data/my.app.package/app_ACRA-unapproved uses 0 bytes
D/storage﹕ App uses 13003529 total bytes

我能看到的是:

  • 僅由Glide用於圖片加載的緩存需要3MB
  • SQLite數據庫需要500kB
  • 共享首選項需要600B
  • 我以前所有Webview的緩存仍然需要9MB
  • files和其他文件夾下的其余文件主要由ACRA用於跟蹤錯誤並占用10kB

最后,我終於發現我的大部分數據都轉到了Webview緩存,實際上並沒有明確存儲為緩存。 我刪除了這些文件,它實際上減少了我的應用程序的大小20MB,甚至超過上面列出的。 我現在知道我的應用程序數據的數量級。

沒有存儲泄漏。

你沒有計算odex (dalvik)或oat (android運行時)文件。它們通常位於

/data/dalvik-cache/xxx.odex
/data/dalvik-cache/<target-architecture>/xxx.oat

這些文件由系統生成,以便在安裝期間進行優化。

你也沒有計算你所在的APK文件

/data/app/xxx.yyy.zzz.apk

如果設備未植根,則無法從adb shell訪問目錄或文件。

我認為設置中的存儲使用情況包括以下三個部分

/data/data/xxx.yyy.zzz
/data/app/xxx.yyy.zzz.apk
odex or oat file

因此,您在/data/data/xxx.yyy.zzz下計算的存儲空間大小始終小於設置中的總大小。

您可以使用MAT TOOL優化應用程序中的內存/大小問題。它會使用更多內存顯示應用程序中的哪個部分。

Android-studio中運行您的應用程序並轉到工具 - > Android-> AndroidDeviceMonitor ,運行您的方案並在設備監視器中單擊以下載您的應用程序.hprof文件 ,請按照下面附帶的圖像 下載.hprof文件

之后,您需要使用sdk-> platform-tools中的 hprof-conv.exe將Android-studio .hprof文件轉換為Eclipse Mat支持的.hprof文件,並按照CMD promt中的cmd進行操作

F:\Android_Studio_SDK\platform-tools>hprof-conv "C:\Users\Bala\Desktop\your_AS_file.hprof" "C:\Users\Bala\Desktop\MAT_File_Name.hprof"

並在MAT工具中轉到文件 - > OpenHeapDump打開你的.hprof文件,它將顯示你的應用程序內存利用package,class,object..etc;

有關推薦MAT工具的推薦鏈接
鏈接1
鏈接2

您可以使用Leak Canary這樣的庫來自動檢測應用程序內的所有內存泄漏: https//corner.squareup.com/2015/05/leak-canary.html

您還可以訪問Android Studio中的DDMS,並在不編碼任何內容的情況下獲取應用程序中存儲的更多信息。 但是,泄漏金絲雀會檢測到大部分泄漏。

希望能幫助到你!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM