[轉載自:http://mobile.51cto.com/iphone-274229.htm]php
Cocoa對象 根類是本文要介紹的內容,僅憑Objective-C語言和運行環境並不足以構造哪怕是最簡單的面向對象的程序,至少是不容易的。還缺乏一些東西:即全部對象公有的基本行爲和接口的定義。根類正是提供了這些定義。java
之因此叫根類,是由於它位於整個類層次(這裏是指Cocoa的類層次)的根上。根類不從其它類繼承,可是類層次中的全部其它類都最終從根類繼承下來。根類連同Objective-C語言,是Cocoa直接訪問Objective-C運行環境或與之交互的基本途徑。Cocoa對象的大部分對象行爲能力都是從根類獲得的。編程
Cocoa提供了兩個根類:NSObject和NSProxy。Cocoa將後者定義爲抽象類,用於表示其它對象的替身對象。所以NSProxy類在分佈式對象架構中是很重要的。因爲做用比較特別,NSProxy在Cocoa程序中出現頻率很低。Cocoa開發者在提到根類時,幾乎老是指NSObject。數據結構
本部分將討論NSObject類,看看它如何與運行環境進行交互,以及它爲全部Cocoa對象定義的基本行爲和接口。其中主要是它爲對象的內存分配、初始化、內存管理、內省、以及運行環境支持所聲明的方法。這些概念是理解Cocoa的基礎。架構
NSObjectiphone
NSObject是大多數Objective-C類層次的根類,它沒有超類。其它類從NSObject繼承訪問Objective-C語言運行時系統的基本接口,它們的實例能夠獲得對象行爲的能力。異步
雖然NSObject不是一個嚴格的抽象類,但它是個虛類。僅憑一個NSObject實例除了做爲一個簡單的對象外,不能完成任何有用的工做。爲了在您的程序中加入特有的屬性和邏輯,必須建立一個或多個從NSObject或其派生類繼承下來的類。分佈式
NSObject採納了NSObject協議(參見"根類—和協議"部分)。NSObject協議支持多個根對象。舉例來講,NSProxy是另外一個根類,它不是繼承自NSObject,但採納了NSObject協議,以便和其它Objective-C對象共用一個公共的接口。函數
NSObject和java.lang.Object一塊兒,是Java版本的Cocoa中全部類的根類,包括Foundation和Application Kit。測試
根類—和協議
NSObject不只僅是一個類的名稱,仍是一個協議的名稱。二者對於定義一個Cocoa對象都是必要的。NSObject協議指定了Cocoa中全部根類必須的基本編程接口,所以不只NSObject類採納了這個同名的協議,其它根類也採納這個協議,好比NSProxy。NSObject類進一步指定了不做爲代理對象的Cocoa對象的基本編程接口。
NSObject及相似的協議用於Cocoa對象的整體定義(而不是在類接口中包含那些協議),使多個根類成爲可能。每一個根類共用一個由它們採納的協議定義的公共接口。
在另外一種意義上,NSObject不只僅是個「根」協議。雖然NSObject類沒有正式採納NSCopying、NSMutableCopying、和NSCoding協議,但它聲明和實現了與那些協議相關的方法(並且,包含NSObject類的NSObject.h頭文件中也包含上面提到的全部四個協議的定義)。對象拷貝、編碼、和解碼是對象行爲的基本部分。不少子類(若是不是絕大多數的話)都但願採納和遵循這些協議。
請注意:其它Cocoa類能夠(並且確實是)經過範疇將方法添加到NSObject中。這些範疇一般是一些非正式的協議,在委託中使用。它們容許委託對象選擇實現範疇中的部分方法。然而,NSObject的範疇並不被認爲是基本對象接口的一部分。
根類方法概述
NSObject根類和它採納的NSObject協議及其它「根」 協議一塊兒,爲全部不做爲代理對象的Cocoa對象指定了以下的接口和行爲特徵:分配、初始化、和複製。NSObject類中的一些方法(包括一些來自協議的方法)用於對象的建立、初始化、和複製:
alloc和allocWithZone:方法用於從某內存區域中分配一個對象內存,並使對象指向其運行時的類定義。
init方法是對象初始化原型,負責將對象的實例變量設置爲一個已知的初始狀態。initialize和load是兩個類方法,它們讓對象有機會對自身進行初始化。
new是一個將簡單的內存分配和初始化結合起來的便利方法。
copy和copyWithZone:方法用於拷貝實現這些(由NSCopying協議定義的)方法的類的實例。但願支持可變對象拷貝的類則須要實現mutableCopy和mutableCopyWithZone:(由NSMutableCopying協議定義)方法。
更多信息請參見 "對象的建立"部分。
對象的保持和清理。下面的方法對面向對象程序的內存管理特別重要:
retain方法增長對象的保持次數。
release方法減小對象的保持次數。
autorelease方法也是減小對象的保持次數,可是以推遲的方式。
retainCount方法返回對當前的保持次數。
dealloc方法由須要釋放對象的實例變量以及釋放動態分配的內存的類實現。
更多信息請參見 Cocoa對象的生命週期
內省和比較。NSObjec有不少方法能夠查詢對象的運行時信息。這些內省方法有助於找出對象在類層次中的位置,肯定對象是否實現特定的方法,以及測試對象是否遵循某種協議。這些方法中的一部分僅實現爲類方法。
superclass和class方法(實現爲類和實例方法)分別以Class對象的形式返回接收者的超類和類。
您能夠經過isKindOfClass:和isMemberOfClass:方法來肯定對象屬於哪一個類。後者用於測試接收者是否爲指定類的實例。isSubclassOfClass:類方法則用於測試類的繼承性。
respondsToSelector:方法用於測試接收者是否實現由選擇器參數標識的方法。instancesRespondToSelector:類方法則用於測試給定類的實例是否實現指定的方法。
conformsToProtocol:方法用於測試接收者(對象或類)是否遵循給定的協議。
isEqual:和hash方法用於對象的比較。
description方法容許對象返回一個內容描述字符串;這個方法的輸出常常用於調試(「print object」命令),以及在格式化字符串中和「%@」指示符一塊兒表示對象。
更多信息請參見 內省 。
對象的編碼和解碼。下面的方法和對象的編解碼(做爲歸檔過程的一部分)有關:
encodeWithCoder:和initWithCoder:是NSCoding協議僅有的方法。前者使對象能夠對其實例變量進行編碼,後者則使對象能夠根據解碼過的實例變量對自身進行初始化。
NSObject類中聲明瞭一些於對象編碼有關的方法:classForCoder:、replacementObjectForCoder:、和awakeAfterUsingCoder:。
進一步信息請參見Cocoa的歸檔和序列化編程指南一文。
消息的轉發。forwardInvocation:和相關的方法容許一個對象將消息轉發給另外一個對象。
消息的派發。以performSelector...開頭的一組方法使您能夠在指定的延遲後派發消息,以及將消息從輔助線程派發(同步或異步)到主線程。
NSObject還有幾個其它的方法,包括一些處理版本和姿態(後者使一個類在運行時將本身表示爲另外一個類)的類方法,以及一些訪問運行時數據結構的方法,好比方法選擇器和指向方法實現的函數指針。
接口規範
某些NSObject方法只是爲了被調用,而另外一些方法則是爲了被重載。舉例來講,大多數子類不該該重載allocWithZone:方法,但必須實現init方法—至少須要實現一個最終調用根類的init方法(請參見"對象的建立"部分)的初始化方法。對於那些指望子類重載的方法,NSObject的實現或者什麼也不作,或者返回一個合理的值,好比self。這些缺省實現使咱們有可能向任意的Cocoa對象—甚至是沒有重載這些方法的對象—發送諸如init這樣得基本消息,而又沒必要冒運行時例外的風險。在發送消息以前,沒必要進行檢查(經過respondsToSelector:方法)。更加劇要的是,NSObject的這些「佔位」方法爲Cocoa對象定義了一個公共的結構,並創建了一些規則,若是全部的對象都遵循這些規則,對象間的交互將更加可靠。
實例方法和類方法
運行環境系統以一種特殊的方式處理根類定義的方法。根類定義的實例方法能夠由實例對象和類對象執行,所以全部類對象均可以訪問根類定義的實例方法。對於任何類對象,若是對象中不包含同名的類方法,就能夠執行根類的全部實例方法。
舉例來講,一個類對象能夠經過發送消息來執行NSObject的respondsToSelector:和performSelector:withObject:實例方法:
請注意,只有根類中定義的實例方法才能夠在類對象中使用。在上面的例子中,若是MyClass從新實現了respondsToSelector:或者performSelector:withObject:方法,則那些新的版本將只能用於實例對象。MyClass的類對象只能執行NSObject類定義的版本(固然,若是MyClass將respondsToSelector:或performSelector:withObject: 實現爲類方法,而不是實例方法,則該類對象能夠執行這些新的實現)。