OC運(yùn)行時(shí)內(nèi)省的4個(gè)方法

對(duì)象在運(yùn)行時(shí)獲取其類(lèi)型的能力稱為內(nèi)省。內(nèi)省可以有多種方法實(shí)現(xiàn)。

OC運(yùn)行時(shí)內(nèi)省的4個(gè)方法:

判斷對(duì)象類(lèi)型:

-(BOOL) isKindOfClass: 判斷是否是這個(gè)類(lèi)或者這個(gè)類(lèi)的子類(lèi)的實(shí)例
-(BOOL) isMemberOfClass: 判斷是否是這個(gè)類(lèi)的實(shí)例

判斷對(duì)象or類(lèi)是否有這個(gè)方法

-(BOOL) respondsToSelector: 判讀實(shí)例是否有這樣方法
+(BOOL) instancesRespondToSelector: 判斷類(lèi)是否有這個(gè)方法

在 Objective-C 中,id類(lèi)型類(lèi)似于(void*) ,可以指向任何類(lèi)的對(duì)象,但在運(yùn)行時(shí)對(duì)象的類(lèi)型不再是id,而是該對(duì)象真正所屬的類(lèi)。
Person *person = [[Person alloc] init];  
NSArray *arr = @[person];
id  obj = arr[0];    //OC集合中取出的對(duì)象都是id類(lèi)型
此時(shí)可通過(guò)
BOOL  isPersonClass = [obj  isKindOfClass: [Person class] ];
來(lái)判斷obj是否Person類(lèi)型或其子類(lèi)的對(duì)象。
在 Objective-C 中,用父類(lèi)類(lèi)型定義的指針,可以指向其子類(lèi)的對(duì)象,但在運(yùn)行時(shí)對(duì)象真實(shí)類(lèi)型會(huì)是子類(lèi)。
//例如 Boy是Person的子類(lèi),現(xiàn)定義:
Person  *p = [[Boy alloc] init];
可通過(guò) BOOL  isBoy = [p  isMemberOfClass: [Boy class] ]; 
判斷Person *類(lèi)型的p是否是Boy類(lèi)型。
在使用代理調(diào)用代理方法時(shí),并不知道代理對(duì)象有沒(méi)有實(shí)現(xiàn)對(duì)應(yīng)方法,如未實(shí)現(xiàn)就會(huì)報(bào)方法找不到的錯(cuò)誤。此時(shí)最好使用respondsToSelector:先判斷下,然后調(diào)用會(huì)比較安全。

另外,可以用來(lái)判斷方法的版本,避免找不到方法報(bào)錯(cuò)。

例如:iOS8以后UIApplication新增注冊(cè)遠(yuǎn)程通知的方法,如果ios7及以下系統(tǒng)中調(diào)用[application registerForRemoteNotifications];立即會(huì)崩潰。

@interface UIApplication (UIRemoteNotifications)
- (void)registerForRemoteNotifications NS_AVAILABLE_IOS(8_0);
@end

此時(shí)可以用respondsToSelector來(lái)判斷:

if ([application respondsToSelector:@selector(registeredForRemoteNotifications)])
    { //IOS8
        [application registerForRemoteNotifications];
    }
else { // ios7
#pragma clang diagnostic push
#pragma clang diagnostic ignored"-Wdeprecated-declarations"  
//夾在3個(gè)#pragma中間的不報(bào)方法過(guò)期警告
        [application registerForRemoteNotificationTypes:(UIRemoteNotificationTypeBadge | 
UIRemoteNotificationTypeSound | UIRemoteNotificationTypeAlert)];
#pragma clang diagnostic pop
    }

/*
如果不知道某個(gè)方法在哪個(gè)版本出現(xiàn)的,就可以用respondsToSelector來(lái)判斷以避免崩潰。
當(dāng)然也可以先判斷[UIDevice currentDevice].systemVersion.floatValue >= 8.0,
再調(diào)用registerForRemoteNotifications方法。
*/
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容