元類(Meta Class)
元類存儲(chǔ)著一個(gè)類的所有類方法,當(dāng)我們向一個(gè)對(duì)象發(fā)送消息時(shí),runtime會(huì)在這個(gè)對(duì)象所屬的這個(gè)類的方法列表中查找方法;而向一個(gè)類發(fā)送消息時(shí),會(huì)在這個(gè)類的meta-class的方法列表中查找。
類(Class)
Objective-C類是由Class類型來表示的,它實(shí)際上是一個(gè)指向objc_class結(jié)構(gòu)體的指針。它的定義如下:
typedef struct objc_class *Class;
objc/runtime.h中objc_class結(jié)構(gòu)體的定義如下:
struct objc_class {
Class isa OBJC_ISA_AVAILABILITY;
#if !__OBJC2__
// 父類
Class super_class OBJC2_UNAVAILABLE;
// 類名
const char *name OBJC2_UNAVAILABLE;
// 類版本信息
long version OBJC2_UNAVAILABLE;
// 類信息
long info OBJC2_UNAVAILABLE;
// 類實(shí)例變量大小
long instance_size OBJC2_UNAVAILABLE;
// 類成員變量列表
struct objc_ivar_list *ivars OBJC2_UNAVAILABLE;
// 類方法列表
struct objc_method_list **methodLists OBJC2_UNAVAILABLE;
// 類方法緩存
struct objc_cache *cache OBJC2_UNAVAILABLE;
// 類協(xié)議列表
struct objc_protocol_list *protocols OBJC2_UNAVAILABLE;
#endif
} OBJC2_UNAVAILABLE;
isa:在Objective-C中,類自身也是一個(gè)對(duì)象,這個(gè)對(duì)象的isa指針指向metaClass(元類)
super_class:指向該類的父類,如果該類已經(jīng)是最頂層的根類(如NSObject或NSProxy),則super_class為NULL。
cache:用于緩存最近使用的方法。一個(gè)接收者對(duì)象接收到一個(gè)消息時(shí),它會(huì)根據(jù)isa指針去查找能夠響應(yīng)這個(gè)消息的對(duì)象。在實(shí)際使用中,這個(gè)對(duì)象只有一部分方法是常用的,很多方法其實(shí)很少用或者根本用不上。這種情況下,如果每次消息來時(shí),我們都是methodLists中遍歷一遍,性能勢(shì)必很差。這時(shí),cache就派上用場(chǎng)了。在我們每次調(diào)用過一個(gè)方法后,這個(gè)方法就會(huì)被緩存到cache列表中,下次調(diào)用的時(shí)候runtime就會(huì)優(yōu)先去cache中查找,如果cache沒有,才去methodLists中查找方法。這樣,對(duì)于那些經(jīng)常用到的方法的調(diào)用,但提高了調(diào)用的效率。
version:我們可以使用這個(gè)字段來提供類的版本信息。這對(duì)于對(duì)象的序列化非常有用,它可是讓我們識(shí)別出不同類定義版本中實(shí)例變量布局的改變。
類的實(shí)例對(duì)象(id)
typedef struct objc_object *id;
objc/objc.h中objc_object結(jié)構(gòu)體的定義如下:
struct objc_object {
Class isa OBJC_ISA_AVAILABILITY;
};
該結(jié)構(gòu)體isa指向?qū)ο笏鶎俚念悺.?dāng)我們向一個(gè)Objective-C對(duì)象發(fā)送消息時(shí),運(yùn)行時(shí)庫會(huì)根據(jù)實(shí)例對(duì)象的isa指針找到這個(gè)實(shí)例對(duì)象所屬的類。Runtime庫會(huì)在類的方法列表及父類的方法列表中去尋找與消息對(duì)應(yīng)的selector指向的方法。找到后即運(yùn)行這個(gè)方法。