2014年12月21日 星期日

Protocol 協定

介紹

在 Objective-C 裡,每一個類別是單繼承的,一個類別只會有一個父類別,而這個父類別也只會有一個父類別,這樣一直往上追朔直到根類別 NSObject,但如果你需要呼叫一個不在這整個繼承鏈裡的方法,protocol 協定就是一個可以幫你解決這個問題的方法(註一)。

製作 protocol


解說:
  • protocol 本身不會實作,只會宣告 method,實作的部分由使用這個 protocol 的 class 來實作。
  • 在Objective-C 2.0 之後,加了 @required 跟 @optional 的語法,你可以設定某些method是optional,也就是這些 method 沒有一定要實作出來。預設是 @required,要注意的是@required跟 @optional 這兩個語法的影響範圍,是從它以下所有的 method 都會被影響,直到另一個 directive 或是 @end 為止。
  • 就像 class 可以繼承另一個 class 裏所有的 method 一樣,protocol 也可以繼承自另一個 protocol,大多數的 protocol 都是繼承自 <NSObject> 這個根 protocol(註二),但我們並不需要實作 <NSObject> 裡的 method,因為不管是我們自定或是系統提供的 class 都會繼承自 NSObject 這個 class,自然也就有 <NSObject> 的實作了(註三)。

為了讓程式模組化,會建議把 protocol獨立寫在一個標頭檔(Header File)裡。


    使用 protocol

    方法如下,如果要一次使用多個 protocol 用逗號分開就可以了:

    定義變數

    protocol 也可以當作一種型別來定義變數。
    這段程式的意思是:delegate 這個變數,它可以是任意資料型態,但一定要遵循 protocolName 這個 protocol,也就是說,delegate 的實體必需要實作 protocolName 裡@required所有的  method。


    這種用 @protocol 來定義方法的稱做 formal protocol,從名字看大概猜得出來一定也有叫做 informal protocol 的東西,不過這個會在介紹 category 的時候再做說明。


    註一:另一種對於 protocol 使用的說法:對於繼承自不同父 class 的 class 來說,如果需要有共同的方法名稱,就需要使用 Protocol。我還沒完全搞清楚@@
    註二:每次要建立新的 protocol 時,Xcode都會自訂幫我們繼承 <NSObject>,但我發現這個可有可無,我把 <NSObject> 刪掉也沒有出現編譯錯誤,我現在還不知道什麼時候要繼承 <NSObject> 什麼時候不用。
    註三:這句其實我沒有完全看懂,因為我沒有看到哪裡有繼承 NSObject class 我也不懂為什麼他說繼承了 NSObject class, 裏的 method 就會自動幫你實作,但確實我沒有實作 NSObject class 裏的 method 也沒出現編譯警告。


    資料整理自:
    Objective-C: Protocols
    http://shenfive.pixnet.net/blog/post/49325290-protocol-語法

    Protocol in Objective-C 高見龍
    Protocol 協定的使用方式 Furnace iOS 程式設計中文學習網站
    http://iosdevelopersnote.blogspot.tw/2010/11/protocol-delegate.html




    蘋果官方文件:Programming with Objective-C:Working with Protocols