详解iOS内存管理机制内部原理

本文详细介绍了iOS内存管理机制,包括栈区、堆区和常量区的划分,以及内存管理的三种方法:TaggedPointer、NONPOINTER_ISA和散列表。TaggedPointer用于节省64位系统中小型数据对象的内存,通过在指针中存储数据和类型信息。此外,文章还探讨了NONPOINTER_ISA的结构和引用计数的存储方式。内存管理中还包括SideTables的哈希映射表,用于存储对象的引用计数。最后,文章对比了MRC和ARC的区别,分析了对象回收过程,包括dealloc方法的调用流程和弱引用的创建与清理。
摘要由CSDN通过智能技术生成

iOS中内存管理机制是开发中一项很重要的知识,了解iOS中内存管理的规则不管是在开发中还是在学习中都能很大程度的帮助我们提升效率。下面我就根据自己的理解,详细梳理一下内存管理相关的知识。

在说内存管理之前,我们首先要了解什么内存。一块内存条,是一个从下至上地址依次递增的结构,内存条中主要分为几大类:栈区(stack)、堆区(heap)、常量区、代码区(.text)、保留区。常量区分为未初始化区域(.bss)和已初始化区域(.data),栈区stack存储顺序是由高地址存向低地址,而堆区是由低地址向高地址存储。内存条中地址由低到高的区域分别为:保留区,代码区,已初始化区(.data),未初始化区(.bss),堆区(heap),栈区(stack),内核区。而程序员操作的主要是栈区与堆区还有常量区。

关于iOS内存管理的方案其实并非只有散列表一种,还有一种更为高效且为内存高效节省空间的方法叫做TaggedPointer,表明加标记的指针,我们可以理解为在是指针内部增加一些特殊的信息。

那么为什么要使用taggedPointer这种内存管理方法呢,其如何达到节省内存的目的呢。举个例子,比如在OC中一个NSNumber对象,在32位中的系统中占用4个字节的空间,但是迁移至64位系统中后,其占用空间达到了8字节,以此类推,所有在64位系统中占用空间会翻倍的对象,在迁移后会导致系统内存剧增,即时他们根本用不到这么多的空间,所以苹果对于一些小型数据,采用了taggedPointer这种方式管理内存。

其主要的原理就是在对象的指针中加入特定需要记录的信息,以及对象所对应的值,在64位的系统中,一个指针所占用的内存空间为8个字节,已足以存下一些小型的数据量了,当对象指针的空间中存满后,再对指针所指向的内存区域进行存储,这就是taggedPointer。距离NSNumber,最低4位用于标记是什么类型的数据(long为3,float则为4,Int为2,double为5),而最高4位的“b”表示是NSNumber类型;其余56位则用来存储数值本身内容。

之前runtime文章中有提到过objc_objcet对象中isa指针分为指针型isa与非指针型isa(NONPOINTER_ISA),运用的便是类似这种技术。下面详细解读一下NONPOINTER_ISA:

在一个64位的指针内存中,第0位存储的是indexed标识符,它代表一个指针是否为NONPOINTER型,0代表不是,1代表是。第1位has_assoc,顾名思义,1代表其指向的实例变量含有关联对象,0则为否。第2位为has_cxx_dtor,表明该对象是否包含C++相关的内容或者该对象是否使用ARC来管理内存,如果含有C++相关内容或者使用了ARC来管理对象,这一块都表示为YES,第3-35位shiftcls存储的就是这个指针的地址。第42位为weak

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值