溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

iOS優(yōu)化內(nèi)存,提升性能 之三

發(fā)布時(shí)間:2020-06-23 01:16:30 來源:網(wǎng)絡(luò) 閱讀:973 作者:iKingLai 欄目:移動(dòng)開發(fā)

高級(jí)內(nèi)存主題


現(xiàn)在你已經(jīng)學(xué)會(huì)了基本的內(nèi)存管理技術(shù),我講介紹一些高級(jí)內(nèi)存主題。


Retain/Relationship生命周期


在舊的內(nèi)存管理世界中,如果對(duì)象A擁有對(duì)象B,當(dāng)對(duì)象Adeallocated時(shí),對(duì)象A必須release對(duì)象B。但是,如果對(duì)象A擁有對(duì)象B,對(duì)象B又擁有對(duì)象A,會(huì)發(fā)生什么呢?


你可以通過調(diào)用release方法,然后把引用設(shè)置為nil來release對(duì)象A。但是,因?yàn)閷?duì)象B仍然擁有對(duì)象A,對(duì)象A的引用計(jì)數(shù)大于0。當(dāng)你release對(duì)象B的時(shí)候同樣如此;它的引用計(jì)數(shù)仍然大于0,因?yàn)閷?duì)象A仍然擁有對(duì)象B。


類似這樣的引用,任何對(duì)象都不會(huì)被deallocated,如圖7-4展示的那樣。


iOS優(yōu)化內(nèi)存,提升性能 之三


對(duì)于新的ARC機(jī)制,這種引用依然存在,如果你有兩個(gè)對(duì)象互相之間有強(qiáng)引用,兩個(gè)對(duì)象都會(huì)泄露。


因此,如果你想兩對(duì)象彼此應(yīng)用,你需要怎么做呢?你需要使用弱引用。


弱引用


iOS優(yōu)化內(nèi)存,提升性能 之三

因此,為了避免循環(huán)引用,只有對(duì)象A持有對(duì)象B的強(qiáng)引用,對(duì)象B只持有對(duì)象A的弱引用。


UIViewController


所有的iPhone應(yīng)用都要用到UIViewController(要不然你在哪里顯示UI?)。因此,理解UIViewController的生命周期能夠幫助你很多重要的事情,例如:

  • 更好的利用內(nèi)存

  • 避免內(nèi)存泄露

  • 提高響應(yīng)


在教學(xué)和培訓(xùn)的時(shí)候,我發(fā)現(xiàn)很多開發(fā)者對(duì)view controller存在嚴(yán)重的誤解,他們并沒有理解view controller的生命周期。在iPhone環(huán)境中,有一些主要的管理過程來控制view controller對(duì)象的生命周期,例如:

  • 加載view

  • 當(dāng)系統(tǒng)需要回收內(nèi)存時(shí)卸載view

  • release view

  • 從UI中顯示或隱藏view


加載view的過程


當(dāng)一個(gè)view controller請(qǐng)求它的view的時(shí)候,它會(huì)檢查view是否已經(jīng)加載到內(nèi)存中。如果沒有,會(huì)加載它然后viewDidLoad方法會(huì)被調(diào)用。圖7-6顯示了加載view的過程。


iOS優(yōu)化內(nèi)存,提升性能 之三

在加載view的過程中,你需要記住一些性能方面的問題:

  • 如果你重寫了loadView方法,你需要?jiǎng)?chuàng)建view的層次結(jié)構(gòu)來顯示UI。這會(huì)導(dǎo)致輕量級(jí)的性能提升,因?yàn)椴恍枰獜膎ib文件加載。

  • 如果你沒有重寫loadView方法,iOS環(huán)境會(huì)自動(dòng)的查找你指定的nib文件或和view controller同名的nib文件。使用nib文件比較好維護(hù)同時(shí)它有拖拉的功能。

  • 如果沒有匹配到任何東西,iOS環(huán)境會(huì)創(chuàng)建一個(gè)新的空的view,然后返回這個(gè)空的view。


卸載view的過程


對(duì)于內(nèi)存和性能來說,這個(gè)過程是非常重要的。主要原因是當(dāng)你的應(yīng)用有內(nèi)存警告和需要回收內(nèi)存時(shí),這個(gè)過程依然在運(yùn)行。在這個(gè)過程中,didReceiveMemoryWarning方法首先被調(diào)用,然后viewDidUnload方法被調(diào)用。在屏幕上顯示的views不會(huì)被卸載。在圖7-7中你可以看到這個(gè)過程。


iOS優(yōu)化內(nèi)存,提升性能 之三

在卸載view的過程中,有很多內(nèi)存和性能方面的問題你需要記?。?br />

  • 確保當(dāng)方法didReceiveWarning被調(diào)用時(shí),你要清除一些重量級(jí)對(duì)象的內(nèi)存緩存,比如圖片緩存。如果你不這樣做的話,iOS系統(tǒng)會(huì)強(qiáng)制關(guān)閉你的應(yīng)用,這是一個(gè)非常糟糕的用戶體驗(yàn)。

  • 這時(shí)你不應(yīng)該清除或release任何view,因?yàn)檫@是不安全的。相反,你應(yīng)該調(diào)用[super didReceiveWarning],這樣父類能夠檢查release這個(gè)subview是否安全。

  • 如果release它的view是安全的,方法viewDidUnload會(huì)被調(diào)用。你可以選擇重寫這個(gè)方法來一些你需要的清理工作。




注意:當(dāng)你重寫加載view的方法時(shí),如init,loadView和viewDidload,必須先調(diào)用父類的方法。但是,如果你重寫清除方法,如didReceiveWarning,viewDidUnload或dealloc,調(diào)用父類的方法必須在方法的尾部。



在viewDidUnload方法中有一些開發(fā)者感到很迷惑的東西。

  • viewDidLoad和LviewDidUnload不是相互對(duì)應(yīng)的。viewDidLoad是在view controller初始化和請(qǐng)求view之后調(diào)用的。viewDidUnload是在收到內(nèi)存警告時(shí)調(diào)用的。在調(diào)用viewDidUnload方法之后,不會(huì)調(diào)用view controller對(duì)象的dealloc方法。卸載的view將會(huì)被deallocated。

  • 在viewDidUnload中,你只能清除你的views;其他對(duì)象將在didReceiveWarning方法中被清除或release。



向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI