【iOS】引用计数

ops/2024/9/25 17:00:21/

引用计数

  • 自动引用计数
  • 引用计数
  • 内存管理的思考方式
    • 自己生成的对象,自己所持有
    • 非自己生成的对象,自己也能持有
    • 不再需要自己持有的对象时释放
    • 无法释放非自己持有的对象

自动引用计数

自动引用计数(ARC,Automatic Reference Counting)是指内存管理中对引用采用自动计数的技术。对于ARC技术来说,最重要的就是***在LLVM编译器中设置ARC为有效状态,就不用再次输入retain和release代码***。

当满足下列条件时,就无须手动输入retain和release代码了

  • 使用XCode4.2或以上版本
  • 使用LLVM编译器3.0或以上版本
  • 编译器选项中设置ARC为有效

引用计数

我们可以用一个房间内开关灯来说明引用计数这个问题,当房间内进入第一个人时开灯,最后一个人离开时关灯,在这个过程中,需要照明的人数就是引用数。

在这里插入图片描述

如上图所示,就是引用计数的原理

那么对于OC对象来说,下图即可展示两者的对应动作:

在这里插入图片描述

如此来说,OC中的内存管理即入下图所示:

在这里插入图片描述

内存管理的思考方式

在内存管理中,正确、客观的思考方式是:

  1. 自己生成的对象,自己所持有
  2. 非自己生成的对象,自己所持有
  3. 不再需要自己持有的对象时释放
  4. 非自己持有的对象无法释放

在上面的思考方式中多次出现“生成”、“持有”、“释放”三个词,在OC内存管理中还有“废弃”一词,下面展示各个词表示的OC方法:

操作对象Objective-C方法
生成并持有对象alloc/new/copy/mutableCopy等方法
持有对象retain方法
释放对象release方法
废弃对象dealloc方法

这些有关 Objective-C 内存管理的方法,实际上不包括在该语言中,而是包含在 Cocoa 框架中用于 OS X、iOS 应用开发。Cocoa 框架中 Foundation 框架类库的 NSObject 类担负内存管理的职责。Objective-C内存管理中的 allocretain/release/dealloc 方法分别指代 NSObject 类的 alloc 类方法、retain 实例方法、release 实例方法和 dealloc 实例方法。


自己生成的对象,自己所持有

使用以下名称开头的方法名意味着自己生成的对象只有自己持有:

  • alloc
  • new
  • copy
  • mutableCopy

代码格式:

objective-c">id obj = [[NSObject alloc] init];
id obj = [NSObject new];
//注意:上面两种生成并持有对象的方法是完全一致的

对于以下这些名称开头的方法名也意味着自己生成并持有对象:

  • allocMyObject
  • newThatObject
  • copyThis
  • mutableCopyYourObject

非自己生成的对象,自己也能持有

除了上述方法以外的方法生成的对象,因为不是自己生成并持有,所以自己不是该对象的持有者。下面举例说明

objective-c">id obj = [NSMutableArray array];[obj retain];
//通过retain方法,非自己生成的对象跟用alloc等方法生成的对象一样,成了自己所持有的。

不再需要自己持有的对象时释放

自己持有的对象,一旦不再需要时,持有者有义务释放该对象,使用release方法释放。

objective-c">id obj = [[NSObject alloc] init];[obj release];

这里举了一个例子说明,当使用retain方法变成自己持有的时候,也可以使用release释放。

无法释放非自己持有的对象

我们在使用alloc等方法或者retain方法将持有者变成自己时,需要在不需要时释放该对象,但是如果是非自己持有的对象,我们不能释放他,如果释放就会造成应用程序崩溃。例如自己生成对象后不需要时释放了两次,就会导致这个问题。

objective-c">id obj = [[NSObject alloc] init];[obj release];[obj release];

这样做,由于第一次已经释放过了,再次释放就会导致应用程序崩溃。


autorelease和release的区别

当我们使用alloc等方法向实现取得的对象存在但是自己不持有就需要用到autorelease方法。下面举例说明:

objective-c">id obj = [[NSObject alloc] init];[obj autorelease];

使用autorelease方法就可以实现,令对象在超出指定的生存范围时能够自动并正确的释放掉,在我们上文中举例的array就是通过调用autorelease实现的,当然,也可以通过retain方法再将其变成自己持有的。

在这里插入图片描述

上图即展示了autorelease和release的区别。


http://www.ppmy.cn/ops/115864.html

相关文章

基于51单片机的两路电压检测(ADC0808)

目录 一、主要功能 二、硬件资源 三、程序编程 四、实现现象 一、主要功能 基于51单片机,通过ADC0808获取两路电压,通过LCD1602显示 二、硬件资源 基于KEIL5编写C代码,PROTEUS8.15进行仿真,全部资源在页尾,提供…

Docker安装和配置MySQL 5.7的完整指南

本指南将详细介绍如何使用Docker安装MySQL 5.7,并进行全面的配置。我们将涵盖从基本安装到性能优化、安全设置、备份策略和监控等各个方面。 1. 准备工作 首先,确保您的系统已经安装了Docker。如果没有,请参考Docker官方文档进行安装。 2. 创建目录结构 创建以下目录结构来…

接口测试面试题及参考答案(汇总),真香

1、你们公司的接口测试流程是怎样的 接口测试我们是在XX项目做的,主要有XX接口,XX接口,XX接口等。 Step1.首先是从开发那里拿到API接口文档,了解接口业务、包括接口地址、请求方式,入参、出参,token鉴权&…

Flexus X实例全方位指南:智能迁移、跨云搬迁加速与虚机热变配能力的最佳实践

目录 前言 一、云迁移关键挑战 1、企业实例选型关键挑战 2、云算力关键挑战之一 3、云算力关键挑战之二 二、本地IT及其他云搬迁到Flexus X实例上的独有优势 1、Flexus X实例超强性能,遥遥领先同规格友商实例 (1)底层多重调优&#x…

分布式数据库管理系统是什么?附应用场景

在当今这个数据驱动的时代,组织面临着数据量爆炸式增长的挑战。随着业务的扩展和用户数量的增加,尤其是在处理大规模数据和高并发请求时,传统的集中式数据库系统逐渐显露出其局限性。如何应对这些数据挑战,分布式数据库管理系统&a…

Android平台Unity3D下如何同时播放多路RTMP|RTSP流?

技术背景 好多开发者,提到希望在Unity的Android头显终端,播放2路以上RTMP或RTSP流,在设备性能一般的情况下,对Unity下的RTMP|RTSP播放器提出了更高的要求。实际上,我们在前几年发布Unity下直播播放模块的时候&#xf…

css边框修饰

一、设置线条样式 通过 border-style 属性设置,可选择的一些属性如下: dotted:点线 dashed:虚线 solid:实线 double:双实线 效果如下: 二、设置边框线宽度 ① 通过 border-width 整体设置…

如何设置显卡驱动以实现深度学习推理的最佳性能

快速解决深度学习推理过程cuda或tensorRT推理速度变慢的办法,记录一下方便自己以后查看。 一、显卡性能设置: 低延时模式——超高、最大帧速度——1000每秒帧数、电源管理模式——最高性能优先 二、管理员权限(命令提示符以管理员身份运行…