返回

类的内存结构分析揭秘

IOS





## 类的内存结构

Objective-C 中的类本质上是一种数据结构,它了对象的属性和行为。类的内存结构主要分为三个部分:实例变量、方法表和 isa 指针。

### 实例变量

实例变量是类的成员变量,它们存储在对象的内存空间中。每个对象都有自己的实例变量,这些实例变量的值可以根据对象的具体状态而变化。

### 方法表

方法表是一个函数指针数组,它存储了类中所有方法的地址。当对象调用某个方法时,系统会根据 isa 指针找到对应的类,然后从方法表中获取该方法的地址,并执行该方法。

### isa 指针

isa 指针是一个指向类的指针,它存储在对象的内存空间中。isa 指针指向对象的所属类,通过 isa 指针,我们可以获取类的信息,例如类的名称、属性和方法等。

## isa 指向关系

isa 指针指向对象的所属类,而类的 isa 指针又指向其元类。元类是类的类,它了类的属性和行为。元类也拥有自己的 isa 指针,它的 isa 指针指向根元类。根元类是所有类的父类,它是 Objective-C 运行时系统中唯一一个没有 isa 指针的类。

通过 isa 指针,我们可以从对象找到它的所属类,再从类找到它的元类,最后找到根元类。这种 isa 指向关系构成了 Objective-C 运行时系统的基础。

## lldb 动态调试

我们可以使用 lldb 动态调试器来探索 isa 指向关系。首先,创建一个 LGPerson 对象的实例 p,然后使用 lldb 动态调试器来查看 p 的 isa 指针:

(lldb) po [p isa]
<_NSConcreteGlobalBlock _LGPerson: 0x1056a3520>


从输出中可以看出,p 的 isa 指针指向了一个名为 `_NSConcreteGlobalBlock _LGPerson` 的类。这个类是 LGPerson 类的元类。

接下来,我们可以查看 `_NSConcreteGlobalBlock _LGPerson` 的 isa 指针:

(lldb) po [[_NSConcreteGlobalBlock _LGPerson isa] isa]
<_NSMetaClass _LGPerson: 0x10569a180>


从输出中可以看出,`_NSConcreteGlobalBlock _LGPerson` 的 isa 指针指向了一个名为 `_NSMetaClass _LGPerson` 的类。这个类就是 LGPerson 类的类,也就是 LGPerson 类的元类。

最后,我们可以查看 `_NSMetaClass _LGPerson` 的 isa 指针:

(lldb) po [[_NSMetaClass _LGPerson isa] isa]
<_NSRootMetaClass: 0x105695620>


从输出中可以看出,`_NSMetaClass _LGPerson`isa 指针指向了一个名为 `_NSRootMetaClass` 的类。这个类就是根元类。

## 总结

通过对 isa 指向关系的分析,我们可以更好地理解 Objective-C 中类的内存结构。isa 指针将对象、类和元类联系在一起,构成了 Objective-C 运行时系统