美文网首页
[iOS]1、OC对象原理

[iOS]1、OC对象原理

作者: 史记_d5da | 来源:发表于2022-02-08 22:24 被阅读0次

    1、类的内存信息

    // Person.h
    @interface Person : NSObject
    @property (nonatomic, strong) NSString *name;
    @property (nonatomic, strong) NSString *sex;
    @property (nonatomic, assign) int age;
    @property (nonatomic, assign) double height;
    @end
    
    // main.m
    int main(int argc, char * argv[]) {
        Person *p = [Person alloc];
        p.name = @"wangfang";
        p.sex = @"男";
        p.age = 17;
        p.height = 180.5;
        return  0;
    }
    
    
    1.1、查看p的内存结构

    x/5gx p

    0x600002d82070: 0x0100000104a49529 0x0000000000000011
    0x600002d82080: 0x0000000104a44058 0x0000000104a44078
    0x600002d82090: 0x4066900000000000
    

    1、打印类的 ISA
    po 0x0100000104a49529 & 0x00007ffffffffff8ULL(ISA_MASK)

    Person
    

    2、打印 double 类型
    e -f f -- 0x4066900000000000
    p/f 0x4066900000000000

    180.0
    

    2、内存对齐原则

    1、数据成员对⻬规则:结构(struct)(或联合(union))的数据成员,第一个数据成员放在offset为0的地方,以后每个数据成员存储的起始位置要从该成员大小或者成员的子成员大小(只要该成员有子成员,比如说是数组,结构体等)的整数倍开始(比如int为4字节,则要从4的整数倍地址开始存储。)
    2、结构体作为成员:如果一个结构里有某些结构体成员,则结构体成员要从其内部最大元素大小的整数倍地址开始存储。(struct a里存有struct b,b里有char,int ,double等元素,那b应该从8的整数倍开始存储。)
    3、收尾工作:结构体的总大小,也就是sizeof的结果,必须是其内部最大成员的整数倍。不足的要补⻬。

    2.1、分析内存对齐
    struct Struct1 {
        double a;  // 8
        char b;    // 1
        int c;     // 4
        short d;   // 2
    }struct1;
    
    struct Struct2 {
        double a;  // 8
        int b;     // 4
        char c;    // 1
        short d;   // 2
    }struct2;
    

    内存对齐图如下


    Struct1
    Struct2

    3、ISA结构体

    shftcls

    以上是 isa 的结构体,其中 shiftcls 存储类的相关信息

    • nonpointer:表示是否对 isa 指针开启指针优化 0:纯 isa 指针,1:不止是类对象地址,isa 中包含了类信息、对象的引用计数等
    • has_assoc:关联对象标志位,0没有,1存在
    • has_cxx_dtor:该对象是否有 C++ 或者 Objc 的析构器,如果有析构函数,则需要做析构逻辑,如果没有,则可以更快的释放对象
    • shiftcls:存储类指针的值。开启指针优化的情况下,在 arm64 架构中有 33 位用来存储类指针。
    • magic:用于调试器判断当前对象是真的对象还是没有初始化的空间
    • weakly_referenced:志对象是否被指向或者曾经指向一个 ARC 的弱变量,
    • deallocating:标志对象是否正在释放内存
    • has_sidetable_rc:当对象引用技术大于 10 时,则需要借用该变量存储进位
    • extra_rc:当表示该对象的引用计数值,实际上是引用计数值减 1, 例如,如果对象的引用计数为 10,那么 extra_rc 为 9。如果引用计数大于 10, 则需要使用到下面的 has_sidetable_rc
      没有弱引用的对象可以更快释放。
      类地址和isa的关联

    1、Person 类的地址
    p/x Person.class

    (Class) $15 = 0x0000000104da9528 Person
    

    2、Person 对象 p 的内存结构
    x/4gx p

    0x600000318cf0: 0x0100000104da9529 0x0000000000000011
    0x600000318d00: 0x0000000104da4058 0x0000000104da4078
    

    3、通过 ISA_MASKp 的运算,得到 Person 类的地址
    p/x 0x0100000104da9529 & 0x0000000ffffffff8ULL

    (unsigned long long) $17 = 0x0000000104da9528
    

    相关文章

      网友评论

          本文标题:[iOS]1、OC对象原理

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