动态方法决议 和 消息转发
来源:互联网 发布:2017淘宝知识产权处罚 编辑:程序博客网 时间:2024/05/08 22:41
如果我们在 Objective C 中向一个对象发送它无法处理的消息,会出现什么情况呢?我们知道发送消息是通过 objc_send(id, SEL, ...) 来实现的,它会首先在对象的类对象的 cache,method list 以及父类对象的 cache, method list 中依次查找 SEL 对应的 IMP;这个是需要对类对象的结构熟悉,不清楚的可以参考我的下一篇文章《object-c 类结构解析》,如果没有找到且实现了动态方法决议机制就会进行决议,如果没有实现动态方法决议机制或决议失败且实现了消息转发机制就会进入消息转发流程,否则程序 crash。也就是说如果同时提供了动态方法决议和消息转发,那么动态方法决议先于消息转发,只有当动态方法决议依然无法正确决议 selector 的实现,才会尝试进行消息转发。
1. 什么是动态方法决议
Objective C 提供了一种名为动态方法决议的手段,使得我们可以在运行时动态地为一个 selector 提供实现。我们只要实现 +resolveInstanceMethod: 或 +resolveClassMethod: 方法,并在其中为指定的 selector 提供实现即可(通过调用运行时函数 class_addMethod 来添加)。这两个方法都是 NSObject 中的类方法,其原型为:
+ (BOOL)resolveClassMethod:(SEL)name;+ (BOOL)resolveInstanceMethod:(SEL)name;
2.消息转发
实现以下这两个方法
- (void)forwardInvocation:(NSInvocation *)anInvocation{ SEL name = [anInvocation selector]; NSLog(@" >> forwardInvocation for selector %@", NSStringFromSelector(name)); Proxy * proxy = [[[Proxy alloc] init] autorelease]; if ([proxy respondsToSelector:name]) { [anInvocation invokeWithTarget:proxy]; } else { [super forwardInvocation:anInvocation]; }}- (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector { return [Proxy instanceMethodSignatureForSelector:aSelector];}
总结
从上面的示例演示可以看出,动态方法决议是先于消息转发的。
如果向一个 Objective C 对象对象发送它无法处理的消息(selector),那么编译器会按照如下次序进行处理:
1,首先看是否为该 selector 提供了动态方法决议机制,如果提供了则转到 2;如果没有提供则转到 3;
2,如果动态方法决议真正为该 selector 提供了实现,那么就调用该实现,完成消息发送流程,消息转发就不会进行了;如果没有提供,则转到 3;
3,其次看是否为该 selector 提供了消息转发机制,如果提供了消息了则进行消息转发,此时,无论消息转发是怎样实现的,程序均不会 crash。(因为消息调用的控制权完全交给消息转发机制处理,即使消息转发并没有做任何事情,运行也不会有错误,编译器更不会有错误提示。);如果没提供消息转发机制,则转到 4;
4,运行报错:无法识别的 selector,程序 crash;
参考:
http://www.cnblogs.com/kesalin/archive/2012/11/14/dynamic_method_resolve.html
http://www.cnblogs.com/biosli/p/NSObject_inherit_2.html
- 动态方法决议 和 消息转发
- cocoa动态方法决议及消息转发
- 动态方法决议与消息转发
- runtime之动态添加方法(动态决议,请求转发)
- runtime 容错机制一:消息的决议和转发
- IOS动态方法决议
- iOS开发------runtime之动态添加方法(动态决议,请求转发)
- iOS的动态创建实例方法和实现消息转发
- [深入浅出Cocoa]之消息(二)-详解动态方法决议(Dynamic Method Resolution)
- [深入浅出Cocoa]之消息(二)-详解动态方法决议(Dynamic Method Resolution)
- [深入浅出Cocoa]之消息(二)-详解动态方法决议(Dynamic Method Resolution)
- [深入浅出Cocoa]之消息(二)-详解动态方法决议(Dynamic Method Resolution)
- [深入浅出Cocoa]之消息(二)-详解动态方法决议(Dynamic Method Resolution)
- iOS消息机制--动态方法解析、消息转发机制
- Runtime(二)动态添加方法以及消息转发机制
- runtime动态添加方法引出的消息转发
- Objective-C运行时编程指南之动态方法决议
- runtime系列3--Dynamic Method Resolution-方法的动态决议
- ACM(一)大数相乘
- Android.9图片说明
- Git学习笔记与IntelliJ IDEA整合
- VC中如何实现窗口的隐藏
- 在文字里放逐自己
- 动态方法决议 和 消息转发
- 谷歌滚动条设置 IE滚动条设置
- Linux网络状态工具ss命令使用详解
- TextView不用获取焦点也能实现跑马灯
- Gotomeeting让新闻工作更便捷效率
- Android屏幕密度(Density)和分辨率的解释
- 安装mysql 5.5.8 Error Nr.1364 authentication_string
- 世界知名网站的架构技术
- 怎么删除github上的仓库