談起設(shè)計(jì)模式,大家在興奮之余難免心生畏懼。興奮的原因是我們能夠靈活而有機(jī)地運(yùn)用設(shè)計(jì)模式,這就意味著編程工作的高效性和產(chǎn)品健壯性、安全性的提高。很多人自豪于能夠透徹掌握“某某設(shè)計(jì)模式”,而面試官們也常常把對(duì)“某某設(shè)計(jì)模式”的掌握程度作為考評(píng)求職者的重要標(biāo)準(zhǔn)之一。設(shè)計(jì)模式的重要性和技巧性可想而知。那么,畏懼從何說(shuō)起呢?設(shè)計(jì)模式是個(gè)很龐雜的知識(shí)體系,即便是同一設(shè)計(jì)模式在不同開(kāi)發(fā)語(yǔ)言環(huán)境下也存在很大的差異,而真正能駕馭設(shè)計(jì)模式的開(kāi)發(fā)者的確不多。
那么,什么是設(shè)計(jì)模式呢?設(shè)計(jì)模式是在特定場(chǎng)景下對(duì)特定問(wèn)題的解決方案,這些解決方案是經(jīng)過(guò)反復(fù)論證和測(cè)試總結(jié)出來(lái)的。實(shí)際上,除了軟件設(shè)計(jì),設(shè)計(jì)模式也被廣泛應(yīng)用于其他領(lǐng)域,比如UI設(shè)計(jì)和建筑設(shè)計(jì)等。
軟件設(shè)計(jì)模式大都來(lái)源于GoF的23種設(shè)計(jì)模式。該書(shū)的設(shè)計(jì)模式都是面向?qū)ο蟮?,在C++、Java和C#領(lǐng)域都有廣泛的應(yīng)用。Cocoa和Cocoa Touch框架中的設(shè)計(jì)模式也基本上是這23種設(shè)計(jì)模式的演變,但是具體來(lái)說(shuō),Cocoa和Cocoa Touch中的設(shè)計(jì)模式仍然存在著差異。
關(guān)于iOS開(kāi)發(fā),我們將重點(diǎn)分析Cocoa框架下的幾個(gè)設(shè)計(jì)模式。當(dāng)然,Cocoa框架下關(guān)于設(shè)計(jì)模式的內(nèi)容遠(yuǎn)不止這些,但為了能在盡量短的時(shí)間內(nèi)讓其為我所用,我們經(jīng)過(guò)審慎地思考并結(jié)合多年的開(kāi)發(fā)經(jīng)驗(yàn),選擇了如下4種設(shè)計(jì)模式:?jiǎn)卫J?、委托模式、觀察者模式和MVC模式.今天南昌購(gòu)物商城開(kāi)發(fā)公司--百恒網(wǎng)絡(luò)和大家一起先來(lái)了解一下單例模式。
單例模式
單例模式的作用是解決“應(yīng)用中只有一個(gè)實(shí)例”的一類問(wèn)題。
1.1 問(wèn)題提出
在一個(gè)iOS應(yīng)用的生命周期中,有時(shí)候我們只需要某個(gè)類的一個(gè)實(shí)例。例如,當(dāng)應(yīng)用程序啟動(dòng)時(shí),應(yīng)用的狀態(tài)由 UIApplication 類的一個(gè)實(shí)例維護(hù),這個(gè)實(shí)例代表了整個(gè)“應(yīng)用程序?qū)ο蟆?,它只能是一個(gè)實(shí)例,其作用是實(shí)現(xiàn)應(yīng)用程序中一些共享資源的訪問(wèn)和狀態(tài)的保持等。
1.2 Objective-C 實(shí)現(xiàn)原理
單例模式一般會(huì)封裝一個(gè)靜態(tài)屬性,并提供靜態(tài)實(shí)例的創(chuàng)建方法,其UML類圖如圖所示。
Objective-C實(shí)現(xiàn)單例設(shè)計(jì)模式類圖
實(shí)現(xiàn)的參考代碼如下:
其中 static Singleton *sharedManager 為靜態(tài)變量,類方為 + (Singleton*)sharedManager 。 sharedManager 方法采用了GCD(Grand Central Dispatch)技術(shù),這是一種基于C語(yǔ)言的多線程訪問(wèn)技術(shù)。在上述代碼中, dispatch_once函數(shù)就是由GCD提供的,它的作用是在整個(gè)應(yīng)用程序生命周期中只執(zhí)行一次代碼塊( ^{…} )。 dispatch_once_t 是GCD提供的結(jié)構(gòu)體,使用時(shí)需要將GCD地址傳給 dispatch_once 函數(shù)。 dispatch_once 函數(shù)能夠記錄該代碼塊是否被調(diào)用過(guò)。
dispatch_once 函數(shù)不僅意味著代碼僅會(huì)被運(yùn)行一次,而且還意味著此運(yùn)行還是線程同步的。也就是說(shuō),當(dāng)我們使用dispatch_once 函數(shù)時(shí),就不再需要使用諸如 @synchronized 之類的語(yǔ)句。
1.3 Swift 實(shí)現(xiàn)原理
使用Swift語(yǔ)言實(shí)現(xiàn)單例設(shè)計(jì)模式的類圖如圖所示。
使用Swift語(yǔ)言實(shí)現(xiàn)單例設(shè)計(jì)模式的類圖
使用Swift語(yǔ)言實(shí)現(xiàn)的單例設(shè)計(jì)模式非常靈活,可以通過(guò)計(jì)算性替代操作(方法),還可以將屬性定義為靜態(tài)屬性。Swift單例設(shè)計(jì)模式實(shí)現(xiàn)的方式有很多,下面是考慮線程安全的單例模式,相關(guān)代碼如下:
上述代碼第①行中的 sharedInstance 是靜態(tài)計(jì)算屬性,通過(guò)該屬性可以獲得單例對(duì)象。第②行代碼用于定義
結(jié)構(gòu)體,其中有兩個(gè)屬性—— instance 和 token ,其中第③行代碼用于定義靜態(tài)屬性 instance ,它用來(lái)保存 Singleton的子單例對(duì)象。第④行代碼定義了靜態(tài)屬性 token ,它是dispatch_once_t 類型。第⑤行代碼用于將 token 地址傳給dispatch_once 函數(shù)。 dispatch_once 函數(shù)能夠記錄該代碼是否被調(diào)用dispatch_once 函數(shù)不僅意味著代碼僅會(huì)被運(yùn)行一次,而且還意味著此運(yùn)行是線程同步的。
第⑥行代碼用于實(shí)例化 Singleton 對(duì)象,第⑦行代碼用于返回實(shí)例。
1.4 應(yīng)用案例
在Cocoa Touch框架中,有 UIApplication 、 NSUserDefaults 和 NSNotificationCenter 等單例類。另外, NSFileManager
和 NSBundle 類雖然屬于Cocoa框架的內(nèi)容,但也可以在Cocoa Touch框架中使用(Cocoa框架中的單例類有NSFileManager 、 NSWorkspace 和 NSApplication 等)。
1. UIApplication
UIApplication 類的實(shí)例提供了應(yīng)用程序的集中控制點(diǎn)來(lái)保持應(yīng)用的狀態(tài)。 UIApplication 實(shí)例總是分配給應(yīng)用程序委托對(duì)象( UIApplicationDelegate ),通過(guò)應(yīng)用程序委托對(duì)象來(lái)響應(yīng)低內(nèi)存、應(yīng)用啟動(dòng)、后臺(tái)運(yùn)行和應(yīng)用終止等事件。在HelloWorld案例中, AppDelegate 就是這個(gè)應(yīng)用程序的委托對(duì)象,它實(shí)現(xiàn)了UIApplicationDelegate 協(xié)議。
UIApplication 類有很多方法和屬性,下面我們重點(diǎn)介紹其中幾個(gè)。
+ sharedApplication 方法。創(chuàng)建和獲得 UIApplication 實(shí)例的靜態(tài)方法。
idleTimerDisabled 屬性。設(shè)定和獲得“空閑時(shí)間禁止”的狀態(tài)。該屬性的默認(rèn)值是 false ,即默認(rèn)情況下系統(tǒng)會(huì)鎖定屏幕。當(dāng)該屬性為 true 時(shí),則不會(huì)開(kāi)啟“空閑時(shí)間禁止”狀態(tài),系統(tǒng)不會(huì)鎖定屏幕。開(kāi)啟這項(xiàng)設(shè)定需要謹(jǐn)慎,它會(huì)使你的應(yīng)用比較耗電。
- openURL :方法??梢源蜷_(kāi)一些內(nèi)置的iOS應(yīng)用,其中包括打開(kāi)瀏覽器、打開(kāi)Google地圖、撥打電話、發(fā)送短信和發(fā)送E-mail等。
打開(kāi)瀏覽器的示例代碼如下:
打開(kāi)Google地圖時(shí),實(shí)際上是通過(guò)內(nèi)置瀏覽器來(lái)打開(kāi)的,示例代碼如下:
其中NSString 的stringByAddingPercentEscapesUsingEncoding : 方 法 將 字 符 串 轉(zhuǎn) 換 為 URL 編 碼。
如“%E6%B8%85%E5%8D%8E%E5%A4%A7%E5%AD%A6”是“清華大學(xué)”的 URL編碼。
撥打電話時(shí),蘋果官方要求使用該方法調(diào)用內(nèi)置撥號(hào)程序,示例代碼如下:
發(fā)送短信時(shí),蘋果官方要求使用該方法調(diào)用內(nèi)置發(fā)送短信程序,示例代碼如下:
發(fā)送E-mail時(shí),這種方式可以發(fā)送簡(jiǎn)單的不帶附件的E-mail,示例代碼如下:
2. NSUserDefaults
單例類 NSUserDefaults 可以很方便地讀取應(yīng)用設(shè)置項(xiàng)目。 + standardUserDefaults 方法是創(chuàng)建和獲得NSUserDefaults 實(shí)例的靜態(tài)方法。
3. NSNotificationCenter
單例類 NSNotificationCenter 提供信息廣播通知,它采用觀察者模式的通知機(jī)制。 + defaultCenter 方法是創(chuàng)建和獲得 NSNotificationCenter 實(shí)例的共享方法。
4. NSFileManager
NSFileManager 提供了訪問(wèn)文件系統(tǒng)的通用操作,可以定位、創(chuàng)建、復(fù)制文件和文件夾。在iOS 5和Mac OS Xv10.7之后,它還可以管理存儲(chǔ)在iCloud上的數(shù)據(jù)。 + defaultManager 方法是創(chuàng)建和獲得 NSFileManager 實(shí)例的方法。
5. NSBundle
NSBundle 提供了動(dòng)態(tài)加載(或卸載)可執(zhí)行代碼、定位資源文件、資源本地化和訪問(wèn)文件系統(tǒng)等功能+mainBundle 方法是創(chuàng)建和獲得 NSBundle 實(shí)例的共享方法。
本文僅限內(nèi)部技術(shù)人員學(xué)習(xí)交流,不得作于其他商業(yè)用途.希望此文對(duì)廣大技人員有所幫助。文章出自:南昌購(gòu)物商城開(kāi)發(fā)公司-百恒網(wǎng)絡(luò)