iOS內(nèi)存深入研究

參考資料:WWDC2018 iOS Memory Deep Dive

WWDC2018 iOS Memory Deep Dive

iOS內(nèi)存深入研究
盡管這篇文章研究iOS怕享,但涉及的內(nèi)容同樣適用于其他平臺。

1.Why reduce memory 為什么減少內(nèi)存

減少內(nèi)存占用狱从,系統(tǒng)整體表現(xiàn)更好撤师,app啟動(dòng)更快,后臺駐留時(shí)間更長

2.Memory Footprint

1)Pages:系統(tǒng)分配的內(nèi)存頁

Pages.jpg

通常16KB

Page types:Clean / Dirty

App的實(shí)際使用內(nèi)存大小 = 頁面數(shù)量 * 頁面大小

App的實(shí)際使用內(nèi)存大小.jpg

2)Memory-mapped files

內(nèi)存映射文件佳励, 是一種在磁盤上的文件,但加載到了內(nèi)存蛆挫,內(nèi)核實(shí)際上是在它們離開磁盤寫入RAM時(shí)進(jìn)行管理的赃承。

3)一個(gè)典型的app內(nèi)存

典型的app內(nèi)存.jpg

有一個(gè)dirty、compressed和一個(gè)clean的內(nèi)存段悴侵。

dirty:有app寫入的內(nèi)存瞧剖,所有堆分配內(nèi)存、已解碼的圖像緩沖可免、Frameworks中的__DATA抓于、__DATA_DIRTY段。

Compressed:

iOS沒有傳統(tǒng)的磁盤交換系統(tǒng)浇借, 卻而代之捉撮,它使用內(nèi)存壓縮器memory compressor, 它是在iOS7中引入的妇垢。

內(nèi)存壓縮器memory compressor:壓縮不訪問的頁面巾遭,解壓訪問的頁面

4)Memory warnings內(nèi)存警告

不要想當(dāng)然的認(rèn)為內(nèi)存警告是app造成的,在一個(gè)低內(nèi)存的設(shè)備上闯估,接到一個(gè)電話灼舍,就可能引發(fā)內(nèi)存警告。

內(nèi)存壓縮器是釋放內(nèi)存變得復(fù)雜涨薪,因?yàn)楦鶕?jù)壓縮的內(nèi)容骑素,實(shí)際上你可以比以前使用更多的內(nèi)存。

5)Caching

在CPU和內(nèi)存之間平衡

記住有內(nèi)存壓縮器

使用NSCache而不是NSDictonary尤辱,在內(nèi)存警告的時(shí)候NSCache會(huì)自動(dòng)釋放

6)典型的內(nèi)存分析

主要分析Dirty和compressed:

內(nèi)存限制:

  每個(gè)設(shè)備不同
  app有一個(gè)相對高的內(nèi)存限制
  Extension有一個(gè)低得多的限制

內(nèi)存超過限制的異常:

內(nèi)存超過限制的異常.jpg

3.高級的工具用于分析和研究App的內(nèi)存占用情況

1)Xcode內(nèi)存測量計(jì)

Xcode內(nèi)存測量計(jì).jpg

2)Instruments

Allocations 分析由你的app所分配的堆

Leaks 檢查一個(gè)進(jìn)程中的內(nèi)存泄漏

VM Tracker 為臟內(nèi)存以及交互內(nèi)存即iOS中的壓縮內(nèi)存分別提供了獨(dú)立的追蹤砂豌,并且告訴你關(guān)于常駐大小的信息厢岂。

VM Tracker.jpg

常駐內(nèi)存、臟內(nèi)存阳距、干凈內(nèi)存關(guān)系:
https://stackoverflow.com/questions/13437365/what-is-resident-and-dirty-memory-of-ios

Virtual Memory trace 虛擬內(nèi)存追蹤:對與app相關(guān)的虛擬內(nèi)存系統(tǒng)的性能進(jìn)行深入的了解塔粒,它提供了虛擬內(nèi)存系統(tǒng)文件。

Virtual Memory trace.jpg

3)Memory debugger

6cef4a038a824f4b836107f40eae95a5_8612451f05fff33eca9340a0eca676f2.jpg.jpg

使用memgraph文件格式存儲(chǔ)有關(guān)App的內(nèi)存使用信息

? 導(dǎo)出內(nèi)存圖

? 搭配命令行工具使用memgraph

第一個(gè)工具:vmmap 通過輸出分配給進(jìn)程的虛擬內(nèi)存區(qū)域筐摘, 它給你的App提供了內(nèi)存消耗的高級分析卒茬, summary參數(shù)是一個(gè)很好的起點(diǎn),它可以打印出很多細(xì)節(jié)咖熟,比如該區(qū)域內(nèi)存大小

顯示進(jìn)程中分配的虛擬內(nèi)存區(qū)

vmmap App.memgraph

Mmap —summary App.memgraph

檢查臟頁面是否有一部分是由鏈接的框架或庫造成的

vmmap -pages App.memgraph | grep '.dylib' | awk '{sum += $6} END { print "Total Dirty Pages:" sum} '

第二個(gè)工具 leaks 在運(yùn)行時(shí)跟蹤堆中的沒有根的對象

leaks App.memgraph

第三個(gè)工具 heap 提供了關(guān)于進(jìn)程堆中對象分配的各種信息圃酵,它可以幫助你追蹤非常復(fù)雜的分配

heap App.memgraphheap App.memgraph -sortBySize

heap App.memgraph -addresses all | <classes-pattern>

heap App.memgraph -addresse NSConcreteData

第四個(gè)工具:malloc_history

malloc_history -callTree App.memgraph address

4)工具的選擇:

工具的選擇.jpg

4.Images

1) 圖片是內(nèi)存中的大對象。

圖片的大小決定內(nèi)存馍管,不是文件的大小郭赐。

如圖片大小2048 px * 1536 px, 圖片文件大小為590KB
,放到內(nèi)存中圖片所占內(nèi)存大腥贩小:2048 pixels x 1536 pixels x 4 bytes per pixel 約等于 10M

2) 圖片為什么占用這么大的內(nèi)存:

圖片為什么占用這么大的內(nèi)存.jpg

Load階段捌锭,將文件加載進(jìn)內(nèi)存

Decode階段,將圖片解壓縮

Render階段罗捎,顯示圖片

3) 圖片渲染格式:

圖片渲染格式.png

每像素1字節(jié)-8字節(jié)的格式观谦,應(yīng)該選擇哪種格式?

不用自己選擇格式桨菜,讓代碼選擇格式:

停止使用UIGraphicsBeginImageContextWithOptions 豁状, 每個(gè)像素4個(gè)自己

開始使用UIGraphicsImageRenderer , iOS 10引入倒得, iOS 12中自動(dòng)為你選擇最好的圖像格式泻红。

使用UIGraphicsBeginImageContextWithOptions.jpg

使用UIGraphicsImageRendererjpg

使用UIGraphicsImageRenderer的方式節(jié)約75%的內(nèi)存。

4) 我們通常對圖像做的另一件事是對它們進(jìn)行下采樣霞掺。

圖像采用處理選擇.jpg

我們不應(yīng)該用UIImage進(jìn)行縮小承桥,如果我們用UIImage繪圖,由于內(nèi)部坐標(biāo)空間變換根悼,這種方法性能并不高,它也會(huì)解壓縮內(nèi)存中的整個(gè)圖像蜀撑。

取而代之挤巡,我們可以使用ImageIO框架,使用streaming API酷麦,只會(huì)生成結(jié)果尺寸大小的圖像矿卑,能節(jié)省內(nèi)存峰值。

使用UIImage繪圖縮小.jpg

這種方法將有一個(gè)內(nèi)存峰值沃饶。

使用ImageIO采用.jpg

使用ImageIO采用快50%

5.在后臺時(shí)候的優(yōu)化

卸載看不到的大資源

兩種方式:

App生命周期

iewController生命周期

6.補(bǔ)充命令:

vmmap —verbose app.memgraph | grep “str”

引用該地址的對象產(chǎn)生堆棧

leaks —trackTree 地址

malloc_history app.memgraph —fullStacks 地址

7.總結(jié):

1)內(nèi)存有限且是是共用資源

2)在Xcode里運(yùn)行的時(shí)候監(jiān)視內(nèi)存使用

3)讓IOS選擇圖片格式

4)使用ImageIO下采樣圖片

5)卸載不載屏幕上的大資源

6)使用memory graphs深入理解內(nèi)存和減少內(nèi)存

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末母廷,一起剝皮案震驚了整個(gè)濱河市轻黑,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌琴昆,老刑警劉巖氓鄙,帶你破解...
    沈念sama閱讀 218,451評論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異业舍,居然都是意外死亡抖拦,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,172評論 3 394
  • 文/潘曉璐 我一進(jìn)店門舷暮,熙熙樓的掌柜王于貴愁眉苦臉地迎上來态罪,“玉大人,你說我怎么就攤上這事下面「淳保” “怎么了?”我有些...
    開封第一講書人閱讀 164,782評論 0 354
  • 文/不壞的土叔 我叫張陵沥割,是天一觀的道長耗啦。 經(jīng)常有香客問我,道長驯遇,這世上最難降的妖魔是什么芹彬? 我笑而不...
    開封第一講書人閱讀 58,709評論 1 294
  • 正文 為了忘掉前任,我火速辦了婚禮叉庐,結(jié)果婚禮上舒帮,老公的妹妹穿的比我還像新娘。我一直安慰自己陡叠,他們只是感情好玩郊,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,733評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著枉阵,像睡著了一般译红。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上兴溜,一...
    開封第一講書人閱讀 51,578評論 1 305
  • 那天侦厚,我揣著相機(jī)與錄音,去河邊找鬼拙徽。 笑死刨沦,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的膘怕。 我是一名探鬼主播想诅,決...
    沈念sama閱讀 40,320評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了来破?” 一聲冷哼從身側(cè)響起篮灼,我...
    開封第一講書人閱讀 39,241評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎徘禁,沒想到半個(gè)月后诅诱,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,686評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡晌坤,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,878評論 3 336
  • 正文 我和宋清朗相戀三年逢艘,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片骤菠。...
    茶點(diǎn)故事閱讀 39,992評論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡它改,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出商乎,到底是詐尸還是另有隱情央拖,我是刑警寧澤,帶...
    沈念sama閱讀 35,715評論 5 346
  • 正文 年R本政府宣布鹉戚,位于F島的核電站鲜戒,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏抹凳。R本人自食惡果不足惜遏餐,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,336評論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望赢底。 院中可真熱鬧失都,春花似錦、人聲如沸幸冻。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,912評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽洽损。三九已至庞溜,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間碑定,已是汗流浹背流码。 一陣腳步聲響...
    開封第一講書人閱讀 33,040評論 1 270
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留延刘,地道東北人旅掂。 一個(gè)月前我還...
    沈念sama閱讀 48,173評論 3 370
  • 正文 我出身青樓,卻偏偏與公主長得像访娶,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個(gè)殘疾皇子觉阅,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,947評論 2 355