这是我参与8月更文挑战的第5天,活动详情查看:8月更文挑战
什么是SEL类型
-
SEL类型代表着方法的签名,在类对象的方法列表中存储着该签名与方法代码的对应关系 -
每个类的方法列表都存储在类对象中
-
每个方法都有一个与之对应的
SEL类型的对象 -
根据一个
SEL对象就可以找到方法的地址,通过方法的地址就可以调用方法
SEL类型的定义
typedef struct objc_selector *SEL
SEL对象的创建
-
将test方法包装成
SEL对象SEL s = @selector(test); -
将一个字符串方法test转换成为
SEL对象SEL s = NSSelectorFromString(@"test");
SEL对象其他用法
-
将
SEL对象转换为NSString对象NSString *str = NSStringFromSelector(@selector(test)); -
调用对象p的test方法
[p performSelector:@selector(test)];- 首先把 test 这个方法名包装成
SEL类型的对象 - 根据
SEL类型找到该类的类对象 - 在类对象的方法列表中找对应的该方法,找到则执行该代码
- 如果没有找到,则根据类对象上的父类对象指针去父类的类对象的方法列表中查找
- 如果找到了则执行,如果依然没有找到,一直往上找,直到基类(
NSObject),如果都没有找到就报错
注意:
在整个操作中有缓存,第一次在方法列表中是一个一个的找,如果找到对应方法,那么就会将该方法放入缓存,之后再用到的时候就直接使用 - 首先把 test 这个方法名包装成
SEL类型的作用
-
配合对象、类来检查对象、类中有没有实现一个方法
注:
如果通过对象调用该方法,则判断对象方法的实现
如果通过类调用该方法,则判断有没有类方法的实现BOOL flag = [p respondsToSelector:test]; BOOL flag = [Person respondsToSelector:test]; -
配合对象或者类来调用某一个
SEL方法//无参数 SEL sel = @selector(demo); [p performSelector:sel]; //有一个参数 SEL sel = @selector(demo:); [p performSelector:sel withObject:@"str"]; //有俩个参数 SEL sel = @selector(demo: withString:); [p performSelector:sel withObject:@"str" withObject:@"str1"]; -
配合对象将
SEL类型作为方法的形参Car *c = [Car new]; SEL sel = @selector(run); Person *p = [Person new]; [p makeObjct:c withSel:sel];