类
声明
在 .h 文件中使用@class 类名;
声明,在 .m 文件中再引入具体头文件,有效避免重复引入。
初始化类时,如果不需要额外参数,则[[Class alloc] init]
等同于[Class new]
// ByteDancer.h
@interface ByteDancer: NSObject
- (instancetype)initWithName:(NSString *)name;
@end
// ByteDancer.m
@implementation ByteDancer
- (instancetype)initWithName:(NSString *)name {
// 注意!需要调用父类的init
self = [super init];
if (self) {
self.name = name;
}
NSLog(@"A ByteDancer, %@ Joined!", name);
return self;
}
@end
判断是否子类
// 字典对应的不确定类型
NSObject *getValue = [dictionary1 objectForKey:@"key1"];
if ([getValue isKindOfClass:NSString.class]) {
// 确定是NSString 在转型成NSString
NSString *strValue = (NSString *)getValue;
[strValue length];
} else if([getValue isKindOfClass:ByteDancer.class]) {
// 确定是ByteDancer 在转型成ByteDancer
ByteDancer *byteDacner1 = (ByteDancer *)getValue;
[byteDacner1 sayHello];
} else {
NSLog(@"unkown class");
}
协议
协议的声明
// ByteDancerProtocol.h
@protocol SeniorLevel <NSObject>
- (void)doCodeReview;
@end
@protocol JuniorLevel <NSObject>
// id<SeniorLevel> 代表任何遵守SeniorLevel的类
- (void)assignMentor:(id<SeniorLevel>)mentor;
@end
@protocol Developer <NSObject>
- (bool)doCoding;
@end // 协议可以继承多个协议
@protocol ClientDeveloper <Developer>
@end
协议的遵循
#import "ByteDancerProtocol.h"
// ByteDancer.h
@interface SenioriOSDeveloper
: ByteDancer <SeniorLevel, ClientDeveloper>
@end
@interface JunioriOSDeveloper
: ByteDancer <JuniorLevel, ClientDeveloper>
// myMentor 类型是任何遵守 id<SeniorLevel> 的类
@property (strong, nonatomic) id<SeniorLevel> myMentor;
@end
方法
定义

判断能否响应方法
搭配 respondsToSelector 提前确认该对象是否响应消息
通常这种 interface没有声明还要使用performSelector去掉用的情况:
- 第一个可能是这个方法是在运行时透过Runtime添加进来的方法,在编译时不存在
- 第二种可能是在明确知道该对象有些实现私有方法,但没有声明在interface时,会使用 performSelector去掉用
MyClass *myObject = [[MyClass alloc] init];
if ([myObject respondsToSelector: @selector(numerOfDatasFrom:)]) {
int dataCount = [myObject numerOfDatasFrom:@"main"];
NSLog(@"%d", dataCount);
} else {
// MyObject 不回应我的 numerOfDatasFrom 消息(没实现)
int dataCount = -1;
NSLog(@"%d", dataCount);
}
// NSObject.h
@protocol NSObject
/** 发送指定的消息给对象, 返回消息执行结果(相当于方法调用) */
- (id)performSelector:(SEL)aSelector;
/** 发送带一个参数的消息给对象, 返回消息执行结果(相当于方法调用) */
- (id)performSelector:(SEL)aSelector withObject:(id)object;
/** 判断对象是否能够调用给定的方法 */
- (BOOL)respondsToSelector:(SEL)aSelector;
@end
// main.m
// 先判断对象是否能调用方法,再执行调用方法
if ([bytedancer1 respondsToSelector:@selector(sayHello)]) {
// 调用无参无返回值方法
[bytedancer1 performSelector:@selector(sayHello)];
}
// 可以用于调用私有方法
if ([bytedancer1 respondsToSelector:@selector(private_method)]) {
[bytedancer1 performSelector:@selector(private_method)];
}
Objective-C 消息发送与转发机制原理