APP內存占用


一、內存管理
從操作系統的角度來說,內存就是一塊 數據存儲區域,是可被操作系統調度的資源。在多任務(進程)的操作系統中,內存管理尤為重要,操作系統需要為每一個進程合理的分配內存資源。可以從操作系統對內存 分配回收兩方面來理解內存管理機制。
  • 分配機制:為每一個任務(進程)分配一個合理大小的內存塊,保證每一個進程能夠正常的運行,同時確保進程不會占用太多的內存。
  • 回收機制:當系統內存不足的時候,需要又一個合理的回收再分配機制,以保證新的進程可以正常運行。
 
二、Android內存管理
1、內存管理機制
android 系統是基於Linux 內核開發的開源操作系統,而linux系統的內存管理有其獨特的動態存儲管理機制。不過Android 系統對Linux 的內存管理機制進行了優化,Linux 系統會在進程活動停止后就結束該進程,而Android 把這些進程都保留在內存中,直到系統需要更多的內存位置。
 
2、分配機制
Android 為每個進程分配內存的時候,采用了彈性的分配方式,剛開始並不會一下分配很多內存給每個進程,而是給每個進程分配一個“夠用”的量。這個量是根據每一個設備實際的物理內存大小決定的。
隨着應用的運行,當發現當前的內存可能不夠用了,這時Android會為每個進程分配一些額外的內存大小。但這些額外的大小也是有限度的,系統不可能為每一個App分配無限大小的內存。
Android 系統的宗旨是最大限度地讓更多的進程存活在內存中,使得下一次用戶再啟動應用時,不需要重新創建進程,只需要恢復已有的進程就可以,減少應用的啟動時間,提高用戶體驗。
 
3、回收機制
Android 對內存的使用方式是“盡最大限度的使用”,這一點繼承了Linux的優點。Android會在內存中保存盡可能多的數據,即便有些進程不再使用了,但是它的數據還被存儲在內存中,所以 Android現在不推薦顯式的“退出”應用。
當Android 系統發現內存不夠用,需要回收內存的時候,Android 系統就會需要殺死其他進程,來回收足夠的內存,但是 Android 也不是隨便殺死一個進程,比如說一個正在與用戶交互的進程,這種后果是可怕的。所以 Android 會有限清理那些已經不再使用的進程,以保證最小的副作用。
 
 
三、內存分類
在Linux里,一個進程占用的內存有不同說法,具體有以下四種形式:
  • VSS - Virtual Set Size 虛擬耗用內存
  • RSS - Resident Set Size 實際使用物理內存
  • PSS - Proportional Set Size 按比例使用的物理內存
  • USS - Unique Set Size 進程獨自占用的物理內存
 
1、VSS
VSS是單個進程全部可訪問的地址空間,其大小可能包括還尚未在內存中駐留的部分。對於確定單個實際內存使用大小, VSS用處不大。

 

 

2、RSS
RSS 是單個進程實際占用的內存大小,RSS 不太准確的地方在於它包括該進程所使用共享庫全部內存大小。 對於一個共享庫,可能被多個進程使用,實際該共享庫只會被裝入內存一次。

 

 

3、PSS
PSS不同於 RSS,它只是按比例包含其所使用的共享庫大小。 PSS相對於RSS 計算共享庫內存大小是按比例的。例如:3個進程使用同一個占用 30 個內存頁的共享庫。對於三個進程中的任何一個,PSS 將只包含 10 個內存頁。 PSS是一個非常有用的數字,對於系統中的整體內存使用是比較准確的統計。

 

 

4、USS
USS是單個進程私有的內存大小,即該進程獨占的內存部分。USS揭示了一個特定進程在的真實內存增量大小。如果進程終止,USS就是實際被返還給系統的內存大小。

 

 

四、Android內存測試
1、獲取設備內存信息
在Linux中,/proc是一個位於內存中的偽文件系統(in-menory-file system)。該目錄下保存的不是真正的文件和目錄,而是一些運行時信息,如系統內存、磁盤io、設備掛載信息和硬件配置信息等。
使用 adb shell cat /proc/meminfo 查看設備的整體內存使用情況。

 

部分參數含義:
  • MemTotal:表示可供系統支配的內存,系統從開機到加載完成,操作系統內核要保留一些內存,最后剩下可供系統支配的內存就是 MemTotal。
  • MemFree:表示系統尚未使用的內存。
  • MemAvailable:應用程序可用內存大小。
            系統中有些內存雖然已被使用但是可以回收的,比如cache可以回收,所以MemFree不能代表全部可用的內存,這部分可回收的內存加上MemFree才是系統可用的內存,即MemAvailable≈MemFree+系統回收內存。它是內核使用特定的算法計算出來的,是一個估值。它與MemFree 的關鍵區別點在於,MemFree 是系統層面, MemAvailable是應用程序層面。
  • Cached:緩沖區內存大小。
  • Buffers:緩沖區內存大小。

 

2、獲取應用內存占用信息
連接設備,使用 adb shell procrank (手機需要root)來獲取各個應用的 VSS、 RSS、PSS、USS

 

3、獲取指定包的內存占用情況
    adb shell dumpsys meminfo [pkg or pid]
 

 

重點關注參數
一般情況下橫軸僅需要關注 Pss Total 和 Private Dirty 列。Private Dirty 表示進程獨占內存。
  • Native Heap:Native 代碼分配的內存。Native 進程采用C/C++實現,不包含 dalvik 實例的 linux 進程,/system/bin/目錄下面的程序文件運行后都是以 Native 進程形式存在的。
  • Dalvik Heap:Java 對象分配的占據內存
其他參數
  • Dalvik Other:類數據結構和索引占據內存。
  • Stack:棧內存
  • Ashmem:不以dalvik- 開頭的內存區域,匿名共享內存用來提供共享內存通過分配一個多個進程可以共享的帶名稱的內存塊。匿名共享內存(Anonymous Shared Memory-Ashmem)。Android 匿名共享內存是基於Linux 共享內存的,都是在tmpfs 文件系統上新建文件,並將其映射到不同的進程空間,從而達到共享內存的目的,只是Android 在 Linux 的基礎上進行了改造,並借助 Binder+fd 文件描述實現了共享內存的傳遞。
  • Other dev:內部 driver 占用的內存
  • .so mmap:C庫代碼占用的內存
  • .jar mmap:java文件代碼占用的內存
  • .apk mmap:apk代碼占用的內存
  • .ttf mmap:ttf 文件代碼占用的內存
  • .dex mmap:dev 文件代碼占用內存。類函數的代碼和常量占用的內存,dex map 是映射 classex.dex 文件,Dalvik 虛擬機從 dex 文件加載類信息和字符串常量等。Dex 文件有索引區和 Data 區
  • Other mmap:其他文件占用的內存

 

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM