当前位置: 首页 > 网络应用技术

07授权iOS基础层的原理|几个OC对象[实例对象,类对象,元类别],对象的ISA指针,超类,对象的方法调用

时间:2023-03-06 23:54:36 网络应用技术

  以前,当我们探索动画和渲染相关的原理的原理时,我们会输出几篇文章并回答。当我们深深地觉得系统设计师在创建这些系统框架时是如此开放,因此我们决定总结一下《摘要》的摘要。每个子模块的基本原理(详细信息)

  早些时候,探索动画和渲染相关原则的几篇输出文章如下:

  以前的知识:

  根据先前文章的了解,我们终于了解了iOS动画渲染的过程和原理

  最后,我们还基于该概念探索了几个相关问题:iOS Offscreen渲染 - 屏幕渲染,iOS页面结结原理和相应的稳定性治理

  我们对基本原则的探索将总共出口(29篇文章):

  在上一篇文章中,我们探讨了OC的文章:从Objective-C语言的本质中,我提到OC是一种高级编程语言。因此,本文立即探讨了上一篇文章的基本原则的步伐OC的语法并探索OC objects.oc对象主要分为三种类型:

  在通过OC语言编写的程序中,它是一个产生新对象的新对象。在上一篇文章中OC对象的本质中,它是通过讨论NSObject对象的基础探索过程的开始。回顾以前探索的结论,并继续探索!在OC对象的本质中,我们得出了一个结论:

  所有OC课,从本质上是通过...

  我们手头写四个类别:(继承关系如下:)

  @民众

  int _year;

  }

  @结尾

  @Implementation车

  self = [Super Init];

  如果(self){

  _ year = 1;

  }

  返回自我;

  }

  @结尾

  @Interface Carrun:汽车

  - (void)运行;

  @结尾

  @Implementation Carrun

  - (void)运行{

  nslog(@“%s”,func);

  }

  @结尾

  @interface bba_bmw:Carrun {

  @民众

  nsString*_nameplate;//自动铭牌8字节

  }

  @结尾

  @Implementation BBA_BMW

  @结尾

  @interface bba_bmw_runfaster:bba_bmw

  - (void)runfaster;

  @结尾

  @Implementation bba_bmw_runfaster

  nslog(@“%s”,func);

  }

  @结尾

  // map函数:int main(int argc,const char * argv []){

  @autoreleasepool {

  // obj1,obj2是nsobject(实例对象)的实例对象

  nsObject obj1 = [[nsObject alloc] init];

  nsObject obj2 = [[nsObject alloc] init];

  //通过打印,可以看出它们是两个不同的对象,分别占据了两个不同的内存

  nslog(@“ obj1:%p”,obj1);OBJ1);

  nslog(@“ obj2:%p”,obj2);OBJ2);

  // 1.创建一个基类NsObject分配内存的实例

  nslog(@“ nsobject:getInstancesize:%zd”,class_getInstancesize

  nslog(@“ obj-malloc_size:%zd”,malloc_size

  nslog(@“ ====================================================================;

  // 2.创建一个基类NSOBJJECT的子类汽车的实例

  汽车 *汽车= [[CAR ALLOC] INIT];

  nslog(@“ car-getInstancesize:%zd”,class_getInstancesize([car class]));

  nslog(@“ car-malloc_size:%zd”,malloc_size

  nslog(@“ ====================================================================;

  // 3.创建一个汽车子类Carrun分配内存的实例

  Carrun *car_run = [[Carrun alloc] init];

  nslog(@“ carrun-getInstancesize:%zd”,class_getInstancesize([Carrun class]));

  nslog(@“ carrun-mailoc_size:%zd”,malloc_size

  nslog(@“ ====================================================================;

  // 4.创建Carrun的子类BBA_BMW的实例

  bba_bmw *bmw = [[bba_bmw alloc] init];

  nslog(@“ bba_bmw-fininstancesize:%zd”,class_getInstancesize([[bba_bmw class]);

  nslog(@“ bba_bmw-mailoc_size:%zd”,malloc_size

  nslog(@“ ====================================================================;

  // 5.创建Carrun子类BBA_BMW_RUNFASTER分配内存的实例

  bba_bmw_runfaster *bmw_runfaster = [[bba_bmw_runfasfaster alloc] init];

  nslog(@“ bba_bmw_runfaster-getinstancesize:%zd”,class_getInstancesize

  nslog(@“ bba_bmw_runfaster-malloc_size:%zd”,malloc_size

  }

  返回0;

  }

  组合文件:

  从前两个代码中,不难知道其中有一个:我们在正面创建了四个类别,并且具有继承关系的代码将转换为C ++:

  结合先前的继承关系,以及转换为C ++基础代码后的特定情况(如上所示),这不是一个困难的结论:

  注意:类方法一直是类对象,因此,即使您以这种方式编写,也会返回类对象

  让我们检查一下Apple的官方开源运行时代码(代码采集和相关探索过程,请参阅本文:OC的本质),类的底层代码如下:

  查看源代码后,不难得出结论,:

  ....我们已经探索了更常见的...但是,当我们阅读源代码时,我们发现了一个。

  我们继续跳入以查看该函数的实现:我们可以看到ISA对象从此代码调用函数,而ISA指针本身就是

  ISA定义为:

  功能

  内部实施:

  总而言之,得出结论并不难:

  通过引入前长度,我们知道:每个班级都有一个

  通过引入上一个长度,我们知道每个类的类对象和元阶级对象有一个

  我们通过以下代码证明:

  中断点并通过控制台打印相应对象的ISA指针

  我们发现对象 - > isa和对象类是不同的。这是因为从64位开始,ISA需要执行一位操作来计算实际地址。可以通过下载OBJC源代码来找到位操作的值。

  我们通过位操作对其进行验证。

  我们发现Object-ISA指针地址0x001DFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF8-BIT操作以获取ObjectClass 0x00007FFF96537140的地址

  然后,让我们验证类对象的ISA指针是否还需要计算元级对象的地址。当我们以相同的方式打印对象clockass-> isa指针时,我们发现无法打印我们无法打印

  同时,发现左侧的对象类对象中没有ISA指针。

  我相信了解ISA指针的学生熟悉OpoJC_Class结构的内容。今天我不在这里学习。我们只看到第一个对象是ISA指针。为了获得ISA指针的地址,我们创建了相同的结构,我们的车身并通过强制性转换获得了ISA指针。

  此时我们重新验证

  实际上,objectClass2的ISA指针的地址是位操作后元级的地址。

  我们知道是类还是元级对象,类型是类。类和元类的底层是OBJC_CLASS结构的指针。内存是结构。本章探讨了阶级的本质。

  单击课程到室内,我们可以找到

  类对象实际上是指向OBJC_CLASS结构的指针。因此,我们可以说类对象或元阶级对象实际上是内存中的OBJC_CLASS结构。

  当我们来到OBJC_CLASS时,我们可以看到此代码经常出现在基本原理中。

  代码的这一部分被认为在文章中很常见,但这意味着这些代码不再使用。那么OBJC_CLASS的当前结构是什么?我们通过OBJC源代码找到了OOJC_CLASS结构的内容。

  成员变量信息存储在class_ro_t中,我们来class_ro_t进行检查。

  因为某些基础API不能直接在项目中使用,并且我们已经阅读了Apple官方开源的基本代码,因此我们可以模仿官方开源的基本实施,并模仿我们自己的工程定制中类的基础实现结构。如果我们自己写的结构与真实的结构相同,那么当我们强制执行时,我们将一一分配一个相应的作业。然后,我们可以在结构内获取信息。

  以下代码是我们对OBJC_CLASS结构的模仿,提取需要使用的信息,以及定制的结构:(请注意,.m文件为.mm,因为该代码的实现属于C ++语法)))))

  接下来,我们强行将自己的类变成我们的自定义流线型类结构类型。

  通过中断点,我们可以看到类的内部信息。

  在这一点

  首先,让我们看一下实例对象。通过引入以前的空间并不难知道:

  从上图我们可以找到:

  然后,让我们看一下类对象,通过上一个介绍,我们清楚地知道:

  其中,我们发现只有第一个显示第一个

  上图中的IntaceSize = 16也对应于ISA指针8字节+_age4字节+_height4字节中的人对象中的对象。(这不是对ObjectClassData和StudentClassData的分析。基本内容与PersonClassData相同。)

  那么,ISA指针和类对象中的超类指针是那个经典图标吗?让我们对其进行验证。

  通过对上图中的内存地址的分析,我们证明了:

  最后,让我们看一下以前空间中的存储空间:

  

  首先,我们可以看到该结构与PersonClassData相同,并且诸如成员变量和属性列表之类的信息是空的,并且在方法中存储了类似于方法。

  然后验证ISA和超类指针的点是否与上图的序列数相同。

  在上图中,元级点的ISA指向基类的元级,而基类的ISA指针也指向自身。

  在上图中,元级超级类别指向父类的元级,以及类别为“类别类别”类的类。

  本文的整个长度介绍了oc的语法中的几个对象([[实例对象,类对象,元 - 类别])),ISA指示器,超类,对象的对象调用和类的基本本质并验证读取源代码codeUndersand推理。本文仅读取或验证与该主题相关的基础代码,并且尚未引入引入。本文结束,与基础层的其他原理有关的要点等待,等待下次分为

  原始:https://juejin.cn/post/7096087582370431012