Objective-C中的内存管理

        在编程语言中是少不了对内存的管理的,内存对于计算机来说是宝贵的资源,所以对使用不到的资源进行回收是很有必要的。OC中使用引用计数和垃圾回收来管理内存,在OC中为每个对象分配一个引用计数器,当对象刚刚被创建时其初始值为1,当有某段代码需要访问一个对象是时,会将该对象的引用计数器加1(通过retain来实现);当访问一个对象结束时,会将该对象的引用计数器减1(通过release来实现);当计数器为0时,该对象占用的内存空间会被收回。在NSObject类有一个retainCount方法,调用该方法可获取当前对象的引用计数值。

        在XCode4以后的版本采取自动引用计数(Automatic Reference Counting)简称ARC, 默认的是ARC模式,在ARC下是不能直接调用retain,release, releaseCount等方法的,需要在XCode中进行设置,设置如下: 把Objective-C Automatic Reference Counting 改为NO,即可。

    ​    ​之前提到的NSOject类里有个方法,retainCount可以获取当前对象的引用计数的值,废话少说上点代码吧。

    ​    ​1. 用可变的数组结合着可变的字符串来观察一下retainCount的变化。

    ​    ​    ​(1).先创建一个可变数组对象,在创建一个可变字符串对象;

    ​    ​    ​(2).然后往可变数组里添加可变的字符串,观察可变字符串的retainCount的变化。

    ​    ​    ​(3).在可变数组中移除一个str,观察retainCount的变化

    ​    ​    ​(4)我们为什么要用可变的字符串呢?稍后会提到为什么。

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17

//用可变数组来测试内存的访问   NSMutableArray *array = [NSMutableArray arrayWithCapacity:3];   //可变的字符串   NSMutableString *str = [[NSMutableString alloc] initWithString:@"aa"];   //这时的retain = 1;   NSLog(@"新建str时的 strRetain = %d",(int)[str retainCount]);       //把可变字符串对象传入到可变数组中 NSMutalbe的retain会自动加一   //把对象传给另一个对象,此时的retain = 2;   [array addObject:str];   //retain =3;   [array addObject:str];   NSLog(@"添加两个str元素后 strRetain = %d",(int)str.retainCount);       //移除元素   [array removeObjectAtIndex:0];   NSLog(@"移除一个元素后 strRetain = %d",(int)str.retainCount);

   ​    ​    运行的结果:

1 2 3

2014-08-03 19:53:24.449 Memory[2448:303] 新建str时的 strRetain = 1 2014-08-03 19:53:24.449 Memory[2448:303] 添加两个str元素后 strRetain = 3 2014-08-03 19:53:24.450 Memory[2448:303] 移除一个元素后 strRetain = 2

    ​2.NSString的retainCount的变化

    ​    ​    ​用NSString声明的字符串变量的retainCount变化由你初始化字符串时的方式决定

    ​    ​    ​1. 用NSString *str = @"ludashi";定义变量

    ​    ​    ​    ​用上面的方法定义的字符串是常量字符串,他的retianCount为-1或不定,不会随着retian或者release变化而变化

    ​    ​    ​    ​demo如下:

1 2 3 4

NSString *string = @"aa"; NSLog(@"str常量的retainCount = %d",(int)string.retainCount);//retainCount = -1 [string retain]; //没用 NSLog(@"str常量的retainCount = %d",(int)string.retainCount);//retainCount = -1

    ​    ​    ​运行结果:

1 2

2014-08-03 20:01:31.360 Memory[2463:303] str常量的retainCount = -1 2014-08-03 20:01:31.362 Memory[2463:303] str常量的retainCount = -1

   ​    ​    ​2.使用stringWithFormat创建的NSString为变量,系统会进行引用计数。

    ​    ​    ​demo:

1 2 3 4

/*使用stringWithFormat创建的NSString为变量,系统会进行引用计数。*/ NSString *string1 = [NSString stringWithFormat:@"aaaa"]; [string1 retain]; NSLog(@"NSStringFomatRetainCount = %d",(int)string1.retainCount);//retainCount = 2

    ​    ​    ​运行结果:

1

NSStringFomatRetainCount = 2

    ​    ​    ​3 .stringWithString取决于后面跟的string, 后面string的retainCount是多少那么用stringWithString创建的对象就为多少

    ​    ​    ​    ​demo:

1 2 3 4 5 6 7

/*stringWithString取决于后面跟的string, 后面string的retainCount是多少那么用stringWithString创建的对象就为多少*/ NSString *string2 = [NSString stringWithString:string]; NSLog(@"传入字符串常量 RetainCount = %d", (int)string2.retainCount);//retainCount = -1   NSString *string3 = [NSString stringWithString:string1]; NSLog(@"传入的变量FomatRetainCount = %d",(int)string1.retainCount);    //retainCount = 3 NSLog(@"传入的变量RetainCount = %d", (int)string3.retainCount);//retainCount = 3

    ​    ​    ​运行结果:

1 2 3

2014-08-03 20:18:37.240 Memory[2499:303] 传入字符串常量 RetainCount = -1 2014-08-03 20:18:37.240 Memory[2499:303] 传入的变量FomatRetainCount = 3 2014-08-03 20:18:37.240 Memory[2499:303] 传入的变量RetainCount = 3

    ​Objective-C中得ARC(Automatic Reference Counting)

    ​    1.​ARC中应注意的问题:

    ​    ​    ​(1). 不能显式调用dealloc语句, 或者实现或调用retain, release, retianCount 和 autorelease等方法。

    ​    ​    ​(2).不能调用@selector (retain) ,@selector (release)等;

    ​    ​    ​(3).不能使用NSAutoreleasePool对象, 用@autoreleasepool块来代替;

    ​    ​    ​(4).不能用开头new的名称来定义一个属性,除非你定义一个别的getter名称。

    ​    ​

    ​    ​2.ARC特性

    ​    ​    ​ARC增加了新的属性定义关键字,strong来代替retain,表示强引用。用weak来代替assign表示弱引用。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏青玉伏案

Objective-C中的深拷贝和浅拷贝

        在Objective-C中对象之间的拷贝分为浅拷贝和深拷贝。说白了,对非容器类的浅拷贝就是拷贝对象的地址,对象里面存的内容仍然是一份,没有新的内...

21690
来自专栏码生

ios 获取属性的类型

18420
来自专栏Scott_Mr 个人专栏

利用Runtime实现简单的字典转模型

39960
来自专栏DannyHoo的专栏

iOS中防止数组越界之后发生崩溃

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u010105969/article/details/...

28510
来自专栏ios 技术积累

Objective-C 数组筛选

想项目有可能会遇到按照一定条件对某一个数组进行筛选。 直接遍历数组,取符合条件的对象放到一个新数组效率可能不高。

11310
来自专栏陈满iOS

iOS开发·NSString字符串的各种基本操作,数值转换及衍生操作

但有时候,仅仅停留在这些基本操作还不能直接满足一些需求,这时候可以利用这些基本操作进行一些字符串的衍生操作。

31220
来自专栏IMWeb前端团队

Promise的简单实现

本篇文章通过构建一个简单的Promise对象来了解如何做到异步获得数据。 使用方法 const fetch = function(url) { return...

23190
来自专栏一“技”之长

Objective-C中NSArray类的解读

    NSArray数组类是Objective-C语言中常用的也是重要的一个类,除了开发中常用到的一些基础功能,NSArray及其相关类中还封装了许多更加强大...

16620
来自专栏DannyHoo的专栏

iOS开发中子类指针指向父类指针

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u010105969/article/details/...

14820
来自专栏一“技”之长

iOS 中block结构的简单用法 原

自从block出现之后,很多API都开始采用这样的结构,由此可见,block确实有许多优势存在,这里将一些简单用法总结如下:

9230

扫码关注云+社区

领取腾讯云代金券