美文网首页
OC对象的本质

OC对象的本质

作者: 乔克蜀黍 | 来源:发表于2021-09-18 16:41 被阅读0次
    1.一个NSObject对象占用多少内存

    NSObject *obj = [[NSObject alloc] init];,obj占16个字节,系统分配了16个字节给NSObject对象,但NSObject对象内部只使用了8个字节的空间
    NSLog(@"%zd", malloc_size((__bridge const void *)obj));,会输出16
    NSLog(@"%zd", class_getInstanceSize([NSObject class]));,会输出8

    struct NSObject_IMPL {
        Class isa; // 8个字节,NSObject类内部的isa指针占用8个字节
    };
    

    内存对齐:结构体的大小必须是最大成员大小的倍数

    2.对象的isa指针指向哪里
    • instance对象的isa指向class对象
    • class对象的isa指向meta-class对象
    • meta-class对象的isa指向基类的meta-class对象

    获取类的方法

    1. Class objc_getClass(const char *aClassName)
      1> 传入字符串类名
      2> 返回对应的类对象

    2. Class object_getClass(id obj)
      1> 传入的obj可能是instance对象、class对象、meta-class对象
      2> 返回值
      a) 如果是instance对象,返回class对象
      b) 如果是class对象,返回meta-class对象
      c) 如果是meta-class对象,返回NSObject(基类)的meta-class对象

    3. -(Class)class、+ (Class)class
      1> 返回的就是类对象

    - (Class) {
        return self->isa;
    }
    + (Class) {
        return self;
    }
    
    3.OC的类信息存放在哪里
    • 对象方法、属性、成员变量、协议信息,存放在class对象中
    • 类方法,存放在meta-class对象中
    • 成员变量的具体值,存放在instance对象中
    4.instance & class & meta-class
    • instance
      instance对象就是通过类alloc出来的对象,每次调用alloc都会产生新的instance对象,instance对象在内存中存储的信息包括:isa指针、其他成员变量的值
    • class
    NSObject *obj = [[NSObject alloc] init];
    Class objClass = object_getClass(obj); //Runtime API
    

    class对象在内存中存储的信息主要包括
    isa指针、superclass指针、类的属性信息(property)、类的对象方法信息(instance method)、类的协议信息(protocol)、类的成员变量信息(ivar)

    • meta-class
    Class objcMetaClass = object_getClass([NSObject class]); //Runtime API
    

    objectMetaClass是NSObject的meta-class对象(元类对象),每个类在内存中有且只有一个meta-class对象,meta-class对象和class对象的内存结构是一样的,但是用途不一样,在内存中存储的信息主要包括:isa指针、superclass指针、类的类方法信息(class method)

    以下代码获取的objectClass是class对象,并不是meta-class对象
    Class objcClass = [[NSObject class] class];

    5.isa、superclass
    1. instance的isa指向class
    2. class的isa指向meta-class
    3. meta-class的isa指向基类的meta-class
    4. class的superclass指向父类的class,如果没有父类,superclass指针为nil
    5. meta-class的superclass指向父类的meta-class,基类的meta-class的superclass指向基类的class
    6. instance调用对象方法的轨迹,isa找到class,方法不存在,就通过superclass找父类
    7. class调用类方法的轨迹,isa找meta-class,方法不存在,就通过superclass找父类


      isa&superclass
      从64bit开始,isa需要与ISA_MASK进行一次&位运算,才能计算出真实地址 ISA_MASK

    相关文章

      网友评论

          本文标题:OC对象的本质

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