iOS底层探索:isa结构分析

2,434 阅读2分钟

注:本文旨在记录笔者的学习过程,仅代表笔者个人的理解,如果有表述不准确的地方,欢迎各位指正!因为涉及到的概念来源自网络,所以如有侵权,也望告知!

前言

本文主要是深入了解一下OC对象中isa的内部结构。

正文

OC对象的本质

通过翻看OC源码,我们可以看到以下这一样一段代码:

不难发现,对象的本质是一个**结构体。**其中第一个属性便是isa,那么isa到底是什么?它的内部结构又究竟是怎么样的呢?

isa探索

在笔者的另一篇文章中——iOS底层探索:alloc&init,提及到在对象的创建过程中会有一个initInstanceIsa 过程,该过程中会对isa进行初始化,并关联相应的类信息。

既然我们可以知道isa本质是一个isa_t的类型,那么isa_t类型又是怎么样的呢?继续探索,我们可以发现,其实isa_t是一个联合体位域结构,采用这种结构的原因也是基于内存优化的考虑即二进制中每一位均可表示不同的信息)。通常来说,isa指针占用的内存大小是8字节,即64,已经足够存储很多的信息了,这样可以极大的节省内存,以提高性能。

了解isa的具体结构后,我们就来讲解一下,他每一个字段代表的含义吧:

  • 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。

整体如下图片所示: