Objecgtive-C学习实例对象,类对象, 元类对象与 isa指针

文章目录

  • OC对象的本质
  • [实例对象, 类对象, 元类的关系](#实例对象, 类对象, 元类的关系)
    • isa指针概念
      • isa的三条链
        • [第一条: 实例->类对象](#第一条: 实例->类对象)
        • [第二条 类对象 -> 元类](#第二条 类对象 -> 元类)
        • [第三条 元类 -> 根元类 -> 自己](#第三条 元类 -> 根元类 -> 自己)
      • [isa 完整链路图](#isa 完整链路图)
    • 获取元类的方法

OC对象的本质

oc的对象, 类, 主要是基于结构体去实现的

所有的OC对象都继承自NSObject, 类主要是基于结构体去实现的

objc 复制代码
// 类的结构体
struct NSObject_IMPL {
    Class isa; // Class是一个结构体类型, isa是一个结构体指针
}

继承自NSObject 的对象结构大致是, 这是一个继承自NSobject 的对象的Student, (被添加了name 和 age 两个属性)

objc 复制代码
struct Struct_IMPL {
    struct NSObject_IMPL NSobject_IVARS; (Class class) 
    int _age; 
    NSString* _name; 
}

OC的实例对象, 类对象. 元类对象

OC主要包括了3种对象

  1. 实例对象
  2. 类对象
  3. 元类对象

类对象

实例对象就是通过类 alloc 出来的对象 , 每一次调用 alloc 都会产生一个新的instance对象

  1. isa指针
  2. 其他成员变量

类对象

通过实例对象的class方法或类的class方法获取到类对象, 每个类在内存中有且只有一个class 对象

  1. isa指针
  2. superclass指针
  3. 类的属性信息 (@property)
  4. 类的对象方法信息
  5. 类的协议信息
  6. 类的成员变量信息

元类对象

每个类在内存中有且只有一个 元类对象 (meta-class)

  1. isa指针
  2. superclass指针
  3. 类的方法信息

实例对象, 类对象, 元类的关系

在 Objective-C 中,一切皆对象:

  • 普通类对象 :比如 [NSObject class] 获取的是 NSObject 的类对象,用于创建实例([[NSObject alloc] init])。
  • 元类 (Meta Class) :是类对象的 "类",专门存储类方法(+ 开头的方法)的地方。每个类都有且仅有一个元类,类对象的 isa 指针指向元类。

objc_getMetaClass 的核心作用就是获取指定类的元类对象

isa指针概念

每个 OC 对象的第一个成员变量 就是 isa 指针,它指向该对象所属的类,是 OC 消息发送机制的核心。

isa的三条链

第一条: 实例->类对象
objc 复制代码
Dog *dog1 = [[Dog alloc] init];
Dog *dog2 = [[Dog alloc] init];

// 两个实例的 isa 都指向同一个 Dog 类对象
dog1->isa == dog2->isa == [Dog class] // YES

在 Objective-C 中:

  1. 类对象(如Dog类对象)是单例的,程序运行期间只会存在一个。
  2. 每次通过[[Dog alloc] init]创建实例时,新实例的isa成员都会指向这个唯一的Dog类对象,所以dog1->isadog2->isa会指向同一个地址,与[Dog class]的结果也完全相等。

同一个类的所有实例对象的isa指针,都会指向这个类唯一的类对象

第二条 类对象 -> 元类
objc 复制代码
// Dog类对象的 isa 指向 Dog 元类
[Dog class]->isa == objc_getMetaClass("Dog") // YES
```
```
Dog类对象 ──isa──► Dog元类
第三条 元类 -> 根元类 -> 自己
objc 复制代码
// 所有元类的 isa 最终指向 NSObject 元类
// NSObject 元类的 isa 指向自己,形成闭环
Dog元类 ──isa──► NSObject元类 ──isa──► NSObject元类(自己)

isa 完整链路图

复制代码
                    isa                  isa                isa(自己)
Dog实例    ────────────► Dog类对象 ────────► Dog元类 ──────────► NSObject元类
                              │                 │                    │  ▲
               superclass     │   superclass    │    superclass      │  │
                              ▼                 ▼                    ▼  │isa
NSObject实例 ──────────► NSObject类对象 ───► NSObject元类 ───────────┘
                    isa                  isa

这里可以用一张图进行总结

获取元类的方法

objc 复制代码
// 方式一:通过类对象获取元类
Class metaClass = object_getClass([Dog class]);

// 方式二:通过类名字符串获取元类
Class metaClass = objc_getMetaClass("Dog");

// 判断一个 Class 是否是元类
BOOL isMeta = class_isMetaClass(metaClass); // YES

获取元类必须用 object_getClass()objc_getMetaClass(),不能用 [Dog class],因为 [Dog class] 永远返回类对象而不是元类。

相关推荐
列星随旋1 小时前
线段树和树状数组的学习
学习·算法
辰海Coding2 小时前
MiniSpring框架学习-整合 IoC 和 MVC(NPC)
学习·spring·mvc
ytttr8732 小时前
OPC UA 协议栈 C 语言实现
c语言·开发语言·mfc
song5012 小时前
Ascend C 算子开发:从入门到上手
c语言·开发语言·图像处理·人工智能·分布式·flutter·交互
小a杰.3 小时前
Ascend C编程语言进阶:高性能算子开发技巧
android·c语言·开发语言
知识分享小能手4 小时前
Flask入门学习教程,从入门到精通,数据库操作 — 知识点详解与案例代码(4)
数据库·学习·flask
小a杰.5 小时前
Ascend C算子开发实战 - 从零开始写算子
c语言·开发语言
wubba lubba dub dub7505 小时前
第四十八周学习周报
学习
生成论实验室5 小时前
用事件关系网络重新理解AI(三):激活函数、微调与元学习
人工智能·学习·算法·语言模型·可信计算技术
辰海Coding5 小时前
MiniSpring框架学习-为什么一个请求访问 /helloworld,最后能调用到某个 Controller 方法?原始 MVC实现
java·学习·程序人生·spring·mvc