關(guān)聯(lián)
關(guān)聯(lián)是指把兩個(gè)對(duì)象相互關(guān)聯(lián)起來(lái),使得其中的一個(gè)對(duì)象作為另外一個(gè)對(duì)象的一部分
有時(shí)候需要在對(duì)象中存放相關(guān)信息。這時(shí)候我們通常會(huì)考慮從對(duì)象所屬的類中繼承一個(gè)子類。但是有時(shí)候類的實(shí)例可能是由某種機(jī)制所創(chuàng),開(kāi)發(fā)者無(wú)法令這種機(jī)制創(chuàng)建出自己所寫(xiě)的子類實(shí)例。Objective-C提供了一個(gè)鐘強(qiáng)大的特性來(lái)解決這個(gè)問(wèn)題,就是“關(guān)聯(lián)對(duì)象”
使用關(guān)聯(lián),我們可以不用修改類的定義而為其對(duì)象增加存儲(chǔ)空間。這在我們無(wú)法訪問(wèn)到類的源碼的時(shí)候或者是考慮到二進(jìn)制兼容性的時(shí)候是非常有用。
關(guān)聯(lián)是基于關(guān)鍵字的,因此,我們可以為任何對(duì)象增加任意多的關(guān)聯(lián),每個(gè)都使用不同的關(guān)鍵字即可。關(guān)聯(lián)是可以保證被關(guān)聯(lián)的對(duì)象在關(guān)聯(lián)對(duì)象的整個(gè)生命周期都是可用的(在垃圾自動(dòng)回收環(huán)境下也不會(huì)導(dǎo)致資源不可回收)。
創(chuàng)建關(guān)聯(lián)對(duì)象涉及到幾個(gè)方法:
void objc_setAssociatedObject(id object,void *key,id value,objc_AssociationPolicy policy)
以給定的鍵和策略為某個(gè)對(duì)象設(shè)置關(guān)聯(lián)對(duì)象值。
id objc_getAssociatedObject(id object,void *key)
根據(jù)給定的鍵從某個(gè)對(duì)象中獲取相應(yīng)的關(guān)聯(lián)對(duì)象值
void objc_removeAssociatedObjects(id object)
移除指定對(duì)象的全部關(guān)聯(lián)對(duì)象(使用這個(gè)函數(shù),會(huì)斷開(kāi)所有關(guān)聯(lián),使對(duì)象回到初始狀態(tài))
在這里分析一下每個(gè)參數(shù)的含義:
1、id object 源對(duì)象,即宿主
2、void *key 關(guān)鍵字,一個(gè)void類型的指針。每一個(gè)關(guān)聯(lián)的關(guān)鍵字必須是唯一的。通常都是會(huì)采用靜態(tài)變量來(lái)作為關(guān)鍵字,我們可以通過(guò)這個(gè)關(guān)鍵字設(shè)置源對(duì)象的關(guān)聯(lián)對(duì)象,也可以從源對(duì)象獲取關(guān)聯(lián)對(duì)象。此關(guān)鍵字就相當(dāng)于字典中的key,但是兩者有一個(gè)重要的差別:設(shè)置關(guān)聯(lián)對(duì)象是用的key是一個(gè)“不透明的指針”。如果在兩個(gè)鍵上調(diào)用“isEqual”方法的返回值是YES,那么NSDictionary就認(rèn)為二者相等,然而在設(shè)置關(guān)聯(lián)對(duì)象的值是,若想令兩個(gè)鍵匹配到同一個(gè)值,則二者必須是完全相同的指針,所以在設(shè)置關(guān)聯(lián)對(duì)象值時(shí),通常使用靜態(tài)全局變量做鍵。
3、id value 關(guān)聯(lián)對(duì)象,即寄生對(duì)象
4、objc_AssociationPolicy policy 關(guān)聯(lián)策略,關(guān)聯(lián)策略表明了相關(guān)的對(duì)象是通過(guò)賦值,保留引用還是復(fù)制的方式進(jìn)行關(guān)聯(lián)的;還有這種關(guān)聯(lián)是原子的還是非原子的。這里的關(guān)聯(lián)策略和聲明屬性時(shí)的很類似。
| 關(guān)聯(lián)類型 | 等效的@property屬性 |
|---|---|
| OBJC_ASSOCIATIOB_ASSIGN | assign |
| OBJC_ASSOCIATIOB_RETAIN_NONATOMIC | nonatomic,retain |
| OBJC_ASSOCIATIOB_COPY_NONATOMIC | nonatomic,copy |
| OBJC_ASSOCIATIOB_RETAIN | retain |
| OBJC_ASSOCIATIOB_COPY | copy |
實(shí)例: 將一個(gè)數(shù)組關(guān)聯(lián)到一個(gè)字符串上
static char key;
NSArray *array = [NSArray arrayWithObjects:@1,@2,@3,@4,nil];
NSString *str = [NSString stringWithFormat:@"%@",@"1234"];
//設(shè)置關(guān)聯(lián)
objc_setAssociatedObject(str,&key,array,OBJC_ASSOCIATIOB_COPY_NONATOMIC);
//讀取
NSArray *getArray = objc_getAssociatedObject(str,&key);
NSLog("%@",getArray);
//輸出 1,2,3,4
//取消關(guān)聯(lián)
objc_removeAssociatedObjects(str);
//或者重新設(shè)置相應(yīng)key的關(guān)聯(lián)對(duì)象為nil (推薦使用)
//objc_setAssociatedObject(str,&key,nil,OBJC_ASSOCIATIOB_COPY_NONATOMIC);