OC 消息

1. 来看一段OC代码

QKTeacher *teacher = [[QKTeacher alloc] init];
[super setName:@"刘邦"];
[teacher greet];

编译后的代码

QKTeacher *teacher = objc_msgSend(objc_getClass("QKTeacher"), @selector(alloc));
teacher = objc_msgSend(teacher, @selector(init));
struct objc_super teachSuper = {teacher,class_getSuperclass(objc_getClass("QKTeacher"))};
objc_msgSendSuper(&teachSuper, @selector(setName:),@"刘邦");
objc_msgSend(teacher, @selector(greet));

动态添加方法

 + (BOOL)resolveClassMethod:(SEL)sel {
    if ([NSStringFromSelector(sel) isEqualToString:@"newMethord:"]) {
        class_addMethod(self, sel, (IMP)newMethord, "v@:@");
    }
    return [super resolveClassMethod:sel];
}
void newMethord(id self, SEL _cmd,NSString *str) {
    NSLog(@"str : %@",str);
}

// 消息调用
 objc_msgSend(tearcher, @selector(newMethord:),@"刘邦");

小结

  1. 对于[QKTeacher alloc]这样的消息,编译时会转化成objc_msgSend()函数
  2. objc_msgSend() 包括消息的发送者,消息的名字,参数。
  3. objc_msgSend() 有两个隐含的参数 id self 和 SEL _comd
  4. [super setName:@"刘邦"] 这样的消息,编译时会转化成 objc_msgSendSuper
  5. objc_msgSendSuper() 包括父类的结构体指针、方法、方法的参数
  6. struct objc_super 这个结构体里边包括子类的实例,子类的父类的名称

2. OC 消息的运行流程

1.转换成objc_msgSend


objc_msgSend

2.查找方法的实现


查找IMP

3.消息转发

1.1 类方法转发前处理 + (BOOL)resolveClassMethod:(SEL)sel;
1.2 实例方法转发前处理+ (BOOL)resolveInstanceMethod:(SEL)sel
2.重定向消息 - (id)forwardingTargetForSelector:(SEL)aSelector
3.消息转发 - (void)forwardInvocation:(NSInvocation *)anInvocation
4.如果都没处理,就会报找不到消息的异常

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 转至元数据结尾创建: 董潇伟,最新修改于: 十二月 23, 2016 转至元数据起始第一章:isa和Class一....
    40c0490e5268阅读 5,842评论 0 9
  • 消息机制(Messaging) 不知大家有没有想过:我们在程序中调用的方法,是怎么执行的,又是怎么通过一个方法名字...
    百客阅读 5,141评论 0 8
  • 你要知道的runtime都在这里 转载请注明出处 //www.greatytc.com/p/eac6ed1...
    WWWWDotPNG阅读 19,616评论 6 85
  • 哈哈哈哈,看见大家都在写自己的学习总结,本猿在踌躇了三年后终于下定决心也写一些东西。 简单直接,直入主题将是宗旨!...
    大鹏鸟阅读 3,669评论 4 0
  • 你们也许不懂这是什么意思 但懂我的人自然会懂 啊!哈哈!呀! 懂了吗? 呵 也许有些人还是不懂 你不懂我 我不怪你...
    opaque阅读 916评论 0 0