前言
iOS開(kāi)發(fā)筆記(一)
iOS開(kāi)發(fā)筆記(二)
iOS開(kāi)發(fā)筆記(三)
iOS開(kāi)發(fā)筆記(四)
《開(kāi)發(fā)筆記》系列記錄一些開(kāi)發(fā)中遇到的問(wèn)題以及思考。
本文主要回答四個(gè)問(wèn)題:
- 1、對(duì)MVVM框架的了解有哪些?
- 2蠢琳、TextKit的認(rèn)知與運(yùn)用?
- 3、autorelease的原理是什么占业?weak修飾符是什么意思?
- 4江场、performSelector為什么會(huì)有內(nèi)存泄露的提示纺酸?
正文
1、MVVM的一些看法
對(duì)MVVM(Model-View-ViewModel)的嘗試源于用angular-js開(kāi)發(fā)址否。
用過(guò)MVC的人都明白餐蔬,MVC很容易失控成為Massive ViewController。即使通過(guò)業(yè)務(wù)分離佑附、Category劃分功能樊诺,ViewController的代碼量也容易失控膨脹。這種膨脹往往發(fā)生在頁(yè)面內(nèi)容復(fù)雜音同、交互較多的頁(yè)面控制器词爬,需要較多的delegate和target-action代碼。
隨之而來(lái)的是代碼零散化:邏輯相同的代碼零散在各處权均。
在此時(shí)接觸了angular-js顿膨,發(fā)現(xiàn)在一個(gè)復(fù)雜的web頁(yè)面上锅锨,邏輯非常清晰,代碼極其簡(jiǎn)潔恋沃。
于是必搞,嘗試在iOS平臺(tái)使用MVVM:
通過(guò)KVO來(lái)實(shí)現(xiàn)MVVM是其中一種選擇,但是KVO的代碼同樣會(huì)聚在observe的方法囊咏。
希望達(dá)到的效果是:數(shù)據(jù)與頁(yè)面一一對(duì)應(yīng)恕洲,一個(gè)業(yè)務(wù)邏輯代碼盡量聚合。
ReactiveCocoa是了解到最符合我要求的框架梅割。
我對(duì)一個(gè)以前的應(yīng)用進(jìn)行修改霜第,引入ReactiveCocoa并替代原來(lái)的邏輯。
仔細(xì)體驗(yàn)ReactiveCocoa+MVVM后户辞,總結(jié)如下:
MVVM的核心是數(shù)據(jù)綁定泌类、代碼解耦,這與傳統(tǒng)的MVC并不相斥咆课,在對(duì)現(xiàn)有的MVC代碼進(jìn)行優(yōu)化時(shí)末誓,可以為View新建ViewModel來(lái)控制顯示,并通過(guò)get书蚪、set方法來(lái)更新數(shù)據(jù)顯示喇澡。
ReactiveCocoa的優(yōu)點(diǎn)在于邏輯聚合以及響應(yīng)式編程,這在某些產(chǎn)品比如電商類(lèi)的開(kāi)發(fā)上殊校,非常有優(yōu)勢(shì)晴玖。但是ReactiveCocoa增大了開(kāi)發(fā)的難度,在未深入了解其特性時(shí)为流,不易操控呕屎。
所有的架構(gòu),核心都是細(xì)分敬察,解耦秀睛,復(fù)用。
細(xì)分不易出bug莲祸、解耦便于修改蹂安、復(fù)用減少時(shí)間。
沒(méi)有最好的架構(gòu)锐帜,只有相對(duì)合適的架構(gòu)田盈。
2、TextKit
讓程序能夠存儲(chǔ)缴阎,排版和顯示文本信息允瞧,并支持排版所需要的所有特性,包括字距調(diào)整、連寫(xiě)述暂、換行和對(duì)齊痹升。
以下三個(gè)屬性text kit的常用屬性:
//text kit工具
NSTextContainer *_textContainer;
NSLayoutManager *_layoutManager;
NSTextStorage *_textStorage;
再如以下,在- (void)touchesBegan:withEvent:
的兩行代碼
UITouch *touch = [touches anyObject];
NSUInteger characterIdx = [_layoutManager characterIndexForPoint:[touch locationInView:self]
inTextContainer:_textContainer
fractionOfDistanceBetweenInsertionPoints:NULL];
通過(guò)這個(gè)方法贸典,可以獲取到點(diǎn)擊的具體文字视卢,從而實(shí)現(xiàn)對(duì)點(diǎn)擊某些特殊文字進(jìn)行響應(yīng)的功能。
cocoachina上的TextKit的學(xué)習(xí)
3廊驼、自動(dòng)引用計(jì)數(shù)
ARC基本原理:ARC是Automatic Reference Counting(自動(dòng)引用計(jì)數(shù)器)的簡(jiǎn)稱(chēng)。
ARC的規(guī)則就是只要對(duì)象沒(méi)有強(qiáng)指針引用惋砂,就會(huì)被釋放掉妒挎,換而言之 只要還有一個(gè)強(qiáng)引用指針變量指向?qū)ο螅敲催@個(gè)對(duì)象就會(huì)存在內(nèi)存中西饵。弱指針指向的對(duì)象酝掩,會(huì)被自動(dòng)變成空指針(nil指針),從而不會(huì)引發(fā)野指針錯(cuò)誤眷柔。
UIScrollView 就出現(xiàn)過(guò)bug 不是weak期虾,導(dǎo)致動(dòng)畫(huà)結(jié)束崩潰。
GPUstep將引用計(jì)數(shù)保存在對(duì)象內(nèi)存頭部的變量中驯嘱;(簡(jiǎn)單高效镶苞,代碼少)
蘋(píng)果用的散列表(引用計(jì)數(shù)表)管理引用計(jì)數(shù);鞠评;(分配內(nèi)存無(wú)需考慮頭部引用變量茂蚓;表可以追溯到對(duì)象的內(nèi)存塊)
計(jì)數(shù)表更便于調(diào)試(可以追溯),同時(shí)可以方便檢測(cè)持有者是否存在剃幌;
autorelease:NSAutoreleasePool在廢棄(drain)時(shí)聋涨,會(huì)自動(dòng)調(diào)用在期間調(diào)用autorelease對(duì)象的release方法。
如果pool是嵌套生成负乡,那么最內(nèi)側(cè)為使 用時(shí)的pool對(duì)象牍白。
for 循環(huán)持有多個(gè)對(duì)象時(shí),可以使用抖棘。
常用場(chǎng)景:多個(gè)圖片的拼接成視頻茂腥。
如果對(duì)NSAutoreleasePool進(jìn)行autorelease:異常。
ARC是編譯器特性钉答,而不是運(yùn)行時(shí)特性础芍,更不是垃圾回收器(GC);核心就是編譯時(shí)插入相應(yīng)的retian release数尿。
- strong 修飾符:對(duì)象的默認(rèn)修飾符仑性,強(qiáng)引用表示,變量在超出作用域時(shí)會(huì)調(diào)用release方法右蹦。
- weak 修飾符:弱引用的表示诊杆,不持有對(duì)象實(shí)例歼捐;弱引用在對(duì)象被釋放的時(shí)候,會(huì)自動(dòng)重置為nil晨汹;
- unsafe_unretained 修飾符:弱引用的表示豹储,不持有對(duì)象實(shí)例;對(duì)象在被釋放的時(shí)候淘这,不會(huì)重置為nil剥扣;當(dāng)對(duì)象釋放后,再調(diào)用有極大的可能性崩潰铝穷;
- autoreleasing 修飾符:將NSObject 類(lèi)對(duì)象注冊(cè)到autoreleasepool 中钠怯;
遇到占用內(nèi)存越來(lái)越多情況時(shí),可以檢查一些自己是否存在循環(huán)引用導(dǎo)致的內(nèi)存泄露曙聂。
上架前使用Instruments調(diào)試是好習(xí)慣晦炊,循環(huán)引用也可以被檢測(cè)出來(lái)。
額外的文章:ARC下的循環(huán)引用
4宁脊、performSelector的內(nèi)存泄漏
在看完第三點(diǎn)的內(nèi)存管理方式后断国,我們知道在ARC(自動(dòng)引用計(jì)數(shù))調(diào)用方法,編譯器需要知道如何對(duì)返回值進(jìn)行處理榆苞。
返回值的類(lèi)型可以是:void,int,NSString,NSArray,id稳衬,這個(gè)類(lèi)型在頭文件中有聲明,編譯器的處理方式有:
- 1语稠、直接忽略:返回值是基本類(lèi)型宋彼;
- 2、先retain仙畦,不用時(shí)release:返回值是Objective-C類(lèi)型输涕;
- 3、不retain慨畸,不用時(shí)release:init或者copy方法莱坎,或者ns_returns_retained方法;
- 4寸士、autorelease:隨著release pool釋放檐什;(標(biāo)注ns_returns_autoreleased的方法)
調(diào)用performSelector:
時(shí),系統(tǒng)默認(rèn)會(huì)用autorelease的方式弱卡,所以如果方法本應(yīng)用前3種情況乃正,可能會(huì)造成內(nèi)存泄漏。
如果返回值是基本類(lèi)型或者void婶博,那么可以忽略這個(gè)waring瓮具。
5、一些常用的STL
unordered_map 是基于哈希表實(shí)現(xiàn),map的內(nèi)部結(jié)構(gòu)是R-B-tree 紅黑樹(shù)名党。
- 運(yùn)行效率方面:unordered_map最高叹阔,而map效率較低但提供了穩(wěn)定效率和有序的序列;
- 占用內(nèi)存方面:map內(nèi)存占用略低传睹,unordered_map內(nèi)存占用略高,而且是線(xiàn)性成比例的耳幢;
list的size是O(N),因?yàn)闉榱吮WCsplice的效率欧啤;
如果list的size是O(1)睛藻,那么splice就要變成N。
總結(jié)
TextKit部分內(nèi)容不甚滿(mǎn)意邢隧,有待完善修档。