美文网首页
KVO实现原理

KVO实现原理

作者: 小胖纸啦 | 来源:发表于2020-09-24 23:00 被阅读0次
    Person *p1 = [[Person alloc] init];
    Person *p2 = [[Person alloc] init];
    
    // 监听前后对象的类对象有没有变化
    id class1 = object_getClass(p1);
    id class2 = object_getClass(p2);
    
    IMP imp1 = [p1 methodForSelector:@selector(setName:)];
    IMP imp2 = [p2 methodForSelector:@selector(setName:)];
    
    id superClass1 = class_getSuperclass(class1);
    id superClass2 = class_getSuperclass(class2);
    
    NSLog(@"KVO监听前:p1:%@ p2:%@", p1, p2);
    
    NSLog(@"KVO监听前:p1.class:%@ p2.class:%@",class1, class2);
    
    NSLog(@"KVO监听前:imp1:%p imp2:%p",imp1, imp2);
    
    NSLog(@"KVO监听前:superclass1:%@ superclass2:%@",superClass1, superClass2);
    
    [p1 addObserver:self forKeyPath:@"name" options:NSKeyValueObservingOptionNew|NSKeyValueObservingOptionOld context:nil];
    
    class1 = object_getClass(p1);
    class2 = object_getClass(p2);
    
    imp1 = [p1 methodForSelector:@selector(setName:)];
    imp2 = [p2 methodForSelector:@selector(setName:)];
    
    superClass1 = class_getSuperclass(class1);
    superClass2 = class_getSuperclass(class2);
    
    NSLog(@"KVO监听后:p1:%@ p2:%@",p1, p2);
    
    NSLog(@"KVO监听后:p1.class:%@ p2.class:%@",class1, class2);
    
    NSLog(@"KVO监听后:imp1:%p imp2:%p",imp1, imp2);
    
    NSLog(@"KVO监听后:superclass1:%@ superclass2:%@",superClass1, superClass2);

    NSString *methodList1 = [self printPersonMethods:class1];
    NSString *methodList2 = [self printPersonMethods:class2];
    NSLog(@"KVO监听后:methodlist1:%@ \n methodlist2:%@",methodList1, methodList2);
// 没有任何变化
KVO监听前:p1:<Person: 0x6000036287f0> p2:<Person: 0x6000036287d0>
KVO监听后:p1:<Person: 0x6000036287f0> p2:<Person: 0x6000036287d0>

// p1.class: NSKVONotifying_Person p2.class: Person
// p1的类对象发生改变
KVO监听前:p1.class:Person p2.class:Person
KVO监听后:p1.class:NSKVONotifying_Person p2.class:Person

// p1的setName:方法实现IMP指针发生变化
KVO监听前:imp1:0x104e50db0 imp2:0x104e50db0
KVO监听后:imp1:0x10512198b imp2:0x104e50db0

// superclass1:Person superclass2:NSObject
// 所以NSKVONotifying_Person是一个 Person 子类(苹果Runtime动态创建Person的一个子类)
KVO监听前:superclass1:NSObject superclass2:NSObject
KVO监听后:superclass1:Person superclass2:NSObject
methodlist1:[
setName:
class
dealloc
_isKVOA
] 
 methodlist2:[
.cxx_destruct
name
setName:
]
// 打印结果可以看出都有 setName:方法
// 但是 methodList1里面重写了setName: class 和 dealloc 方法,而且还多了一个_isKVOA方法
// 重写setName: 是为了在该方法里面调用_NSSetObjectValueAndNotify()方法
// 重写class方法是为了返回Person类
// 重写dealloc方法是为了向外界隐藏NSKVONotifying_Person子类的存在
// 所以这就是我们开始直接打印p1和p2都是Person类的原因
- (NSString *) printPersonMethods:(id)obj {

    unsigned int count = 0;
    Method *methods = class_copyMethodList([obj class],&count);
    NSMutableString *methodList = [NSMutableString string];
    [methodList appendString:@"[\n"];
    for (int i = 0; i<count; i++) {
        Method method = methods[i];
        SEL sel = method_getName(method);
        [methodList appendFormat:@"%@",NSStringFromSelector(sel)];
        [methodList appendString:@"\n"];
    }

    [methodList appendFormat:@"]"];

    free(methods);

    return methodList;
}

相关文章

  • iOS KVO

    KVO 示例 KVO的实现原理

  • 常见面试题--KVC和KVO

    1、KVO实现原理 2、KVC原理

  • 知识集锦

    https://github.com/starainDou 欢迎点星 KVO实现原理 KVO基本原理: 1 kvo...

  • iOS - 自定义KVO

    之前我们已经了解过了KVO的底层实现原理,不过呢,在我们开始实现自定义KVO之前再来简单回顾下KVO的实现原理 1...

  • iOS - KVO

    [toc] 参考 KVO KVC 【 iOS--KVO的实现原理与具体应用 】 【 IOS-详解KVO底层实现 】...

  • iOS原理篇(一): KVO实现原理

    KVO实现原理 什么是 KVO KVO 基本使用 KVO 的本质 总结 一 、 什么是KVO KVO(Key-Va...

  • iOS高级进阶之KVO

    KVO的原理 分析原理 使用 手动调用 自己实现KVO NSObject+KVOBlock.h NSObject+...

  • iOS 自定义KVO

    通过在了解KVO的实现原理和实现步骤之后,我们可以手动实现KVO,具体可以看最后的demo,这里只讲实现原理 添加...

  • iOS 进阶原理知识笔记

    KVO实现原理 KVO基本原理: 1 kvo是基于runtime机制实现的 2 当某个类的属性对象第一次被观察时,...

  • iOS 进阶原理知识随笔

    KVO实现原理 KVO基本原理: 1 kvo是基于runtime机制实现的 2 当某个类的属性对象第一次被观察时,...

网友评论

      本文标题:KVO实现原理

      本文链接:https://www.haomeiwen.com/subject/vkotuktx.html