美文网首页
每日1道题(day1)

每日1道题(day1)

作者: IreneWu | 来源:发表于2017-05-26 16:26 被阅读164次

    请介绍一下isa指针,怎么用,用来干嘛?

    答:每一个对象内部都有一个isa指针,对象的isa 指针就指向它的真实类型它所属的类.

    isa指针指向顺序:类对象->元类对象->NSObject元类对象。NSObject元类对象 的 isa 指向自己。

    作用:系统提供的 KVO 的实现,就利用了动态地修改 isa 指针的值的技术。

    (万物皆对象。类也是对象,他是meteClass(元类)的实例。)

    扩展:来源:http://www.jianshu.com/p/a0aaf0ffe6e1

    • 实例对象在运行时被表示成objc_object类型结构体,结构体内部有个isa指针指向objc_class结构体。
    • objc_class内部保存了类的变量和方法列表以及其他一些信息,并且还有一个isa指针。这个isa指针会指向meteClass(元类),元类里保存了这个类的类方法列表。
    • 为了完整性,其实元类里也有一个isa指针,这个isa指针,指向的是根元类,根元类的isa指针指向自己
    • 大致如下面逻辑:
      实例对象--(runtime)-->objc_object--(isa)-->objc_class--(isa)-->元类--isa-->根元类--isa-->自己。

    当我们调用某个类的方法时,如果这个类的方法列表里没有该方法,则会去找这个类的父类的方法列表。这种机制就是通过objc_class的第二个变量super_class指针实现的。并且这种继承关系会扩展到元类。

    KVO的实现原理 :

    KVO是通过"isa-swizzling"技术来实现的,当一个对象注册观察者时,这个对象的isa指针被修改指向一个中间类。

    KVO 的实现依赖于 Objective-C 强大的 runtime。当观察A类型的对象时,在运行时会创建了一个继承自A类的NSKVONotifying_A类,且为NSKVONotifying_A重写观察属性的setter 方法,setter 方法会负责在调用原 setter 方法之前和之后,通知所有观察者属性值的更改情况

    假设A类有个name属性,NSKVONotifying_A重写setName方法:

    - (void) setName:(NSString *)name 
    {     
        [self willChangeValueForKey:@"name"];     
        [super setName:name];     
        [self didChangeValueForKey:@"name"]; 
    }
    
    • 被观察属性发生改变之前,willChangeValueForKey:被调用,
    • 通知系统该 keyPath 的属性值即将变更,来保存旧值;
    • 当改变发生后,didChangeValueForKey:被调用,通知系统该 keyPath 的属性值已经变更,
    • 之后observeValueForKey:ofObject:change:context:就会被调用。

    相关文章

      网友评论

          本文标题:每日1道题(day1)

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