OC -内存管理

管理内存有三种方式

1:垃圾回收,在java中常见的管理内存方法,系统自动检测对象是否被使用,是否被释放
2.MRC: 手动管理引用计数,iOS管理内存的方式,程序员通过手动方式来管理对象是否被释放
3.ARC: 自动管理引用计数:基于MRC,系统自动的管理内存

引用计数:retainCount

    当我们使用一个指针指向一块内存的时候,应该对这块内存做retain操作,引用计数+1。当我们不再使用这个指针指向这块内存,应该对这块内存做release操作,引用计数-1。这样可以使引用计数值一直保持等于指向这块内存的指针数量。retainCount返回当前内存的引用计数值。当内存被开辟后,默认的引用计数为1 。

注意:内存管理原则 :加多少,对应减多少,加减做到平衡

1.对象被创建出来之后他的引用计数retainCount就变成1

例子:
 Boy *boy =[[Boy alloc] init];
   NSLog(@"%ld",boy.retainCount);
   结果:2015-07-27 19:30:27.587 OC08,09_内存管理[427:8615] 1

2.retain:对对象的引用计数 +1

例子:
Boy *boy =[[Boy alloc] init];
[boy retain];
NSLog(@"%ld",boy.retainCount);
2015-07-27 19:34:35.190 OC08,09_内存管理          [436:9846] 2

3.release :对对象的引用计数进行 -1 的操作

例子:
Boy *boy =[[Boy alloc] init];
[boy retain];
[boy release];
 NSLog(@"%ld",boy.retainCount);
 2015-07-27 19:36:35.985 OC08,09_内存管理[456:10672] 1

4.当对象的引用计数1 变为 0 的时候,会自动调用dealloc方法,dealloc才是对应对象释放的方法

dealloc在.m文件中实现,dealloc要释放所有不能自己释放的成员变量

例子:

(1)在.h文件中声明三个属性:自定义初始化和便利构造器
@property(nonatomic , retain)NSMutableArray *arr;
@property(nonatomic, copy)NSString *name;
@property(nonatomic, assign)NSInteger age;
-(id)initWithName:(NSString *)name
              age:(NSInteger)age;
+(Person *)personWithName:(NSString *)name
                age:(NSInteger)age;
在.m文件中完成实现:
-(id)initWithName:(NSString *)name
              age:(NSInteger)age{
    self =[super init];
    if (self) {
        self.name=name;
        self.age =age;
                self.arr=[NSMutableArray array];
    }
    return self;
}
+(Person *)personWithName:(NSString *)name
                      age:(NSInteger)age
{
    Person *person=[[Person alloc] initWithName:name age:age];
    return [person autorelease];
}
在最后需要加一步dealloc:
-(void)dealloc
{
    [_arr release];
    [_name release];
    [super dealloc];
}
实现整个类中的成员变量全部释放,在这里因为age是NSInteger类型,在栈区,系统会自动管理,不需要手动释放

上面这些是完整的声明和实现一个类内的成员变量的方法

注意:

1.当对象调用release引用计数是1时,这个对象就不再对他的引用计数进行 -1 的操作,而是直接调用dealloc方法,所以我们在访问对象的引用计数还是 1
2.如果多次对对象进行释放,会造成过度释放,过度释放也是最常见的内存问题

5.NSString 所定义的字符串它的引用计数是 -1

例子:
NSString *str [email protected]"1111";
NSLog(@"%ld",str.retainCount);
结果:2015-07-27 19:54:12.544 OC08,09_内存管理[495:16187] -1

原因:NSString 的对象在全局静态区,它的引用计数是 -1, 代表整数的最大值,其他的对象如可变字符串.字典等都在堆区,他们在被创建出来的初始引用计数都是 1

6.autorelease:未来的某?时刻引?用计数减1。如果内存之前引?用计 数为4,autorelease之后仍然为4,未来某个时刻会变为3。

release和autorelease的区别:release 马上会把对象的引用计数 -1,但是autorelease会延迟把对象的引用计数 -1

例子:
 Boy *boy =[[Boy alloc] init];
   [boy retain];
   [boy retain];
   NSLog(@"%ld",boy.retainCount);
   [boy autorelease];
   NSLog(@"%ld",boy.retainCount);
   结果:
 2015-07-27 20:06:16.356 OC08,09_内存管理[541:20376] 3
 2015-07-27 20:06:16.357 OC08,09_内存管理[541:20376] 3

7.自动释放池

只要对象用autorelease 释放会把对象放入到系统的自动释放池中,等出了池子的范围,对象引用计数自动 -1,这个相当于java 的垃圾回收,对象释放由系统来管理

例子:
 Boy *boy =[[Boy alloc] init];
 [boy retain];
 [boy retain];
 NSLog(@"%ld",boy.retainCount);
 @autoreleasepool {
 [boy autorelease];
 NSLog(@"%ld",boy.retainCount);
  }
 NSLog(@"%ld",boy.retainCount);
结果:
2015-07-27 20:19:02.918 OC08,09_内存管理[573:23991] 3
2015-07-27 20:19:02.919 OC08,09_内存管理[573:23991] 3
2015-07-27 20:19:02.919 OC08,09_内存管理[573:23991] 2

8.对象的所有权:拥有所有权的对象可以对它进行release——–对象如果是我们进行alloc或者retain之后我们就获取了对象的所有权,就可以对对象进行release;

    Boy *b =[Boy boy];
    [b retain];
    NSLog(@"%ld", b.retainCount);
    [b release];

在这里 b 就有了对象的所有权,就可以对对象进行release的操作了

9.遍历构造器在返回对象的时候会加上一个autorelease,所以用便利构造器创建对象不需要对内存进行管理

例子:便利构造器:
+(Boy *)boyWithName:(NSString *)name
              hobby:(NSString *)hobby
{

    Boy *boy=[[Boy alloc] initWithName:name hobby:hobby];
   // 写便利构造器最后别忘了autorelease
    return [boy autorelease];
}

10.对象放入容器

(1).当对象放入到容器Array或字典中,对象会被容器进行一次持有,主要是为了防止空指针问题

(2).等对象从容器中移除掉之后,相应地会 -1

例子:
Boy *boy1 =[[Boy alloc] init];
[boy1 retain];
[boy1 retain];
NSLog(@"%ld",boy1.retainCount);
NSMutableArray *arr = [NSMutableArray arrayWithObjects:boy1, nil];
NSLog(@"%ld",[arr[0] retainCount]);
NSLog(@"%ld",boy1.retainCount);
[arr removeObjectAtIndex:0];
NSLog(@"%ld",boy1.retainCount);
结果:
2015-07-27 20:39:49.255 OC08,09_内存管理[608:31455] 3
2015-07-27 20:39:49.256 OC08,09_内存管理[608:31455] 4
2015-07-27 20:39:49.256 OC08,09_内存管理[608:31455] 4
2015-07-27 20:39:49.256 OC08,09_内存管理[608:31455] 3

(3).对象放到数组里,就可以直接释放对象,对象在数组中可以继续使用,直到数组消失时释放对象

例子:
Boy *b=[[Boy alloc] init];
     NSArray *arr =@[b];
    [b release];

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-10-07 07:43:04

OC -内存管理的相关文章

OC内存管理

OC内存管理 一.基本原理 (一)为什么要进行内存管理. 由于移动设备的内存极其有限,所以每个APP所占的内存也是有限制的,当app所占用的内存较多时,系统就会发出内存警告,这时需要回收一些不需要再继续使用的内存空间,比如回收一些不再使用的对象和变量等. 管理范围:任何继承NSObject的对象,对其他的基本数据类型无效. 本质原因是因为对象和其他数据类型在系统中的存储空间不一样,其它局部变量主要存放于栈中,而对象存储于堆中,当代码块结束时这个代码块中涉及的所有局部变量会被回收,指向对象的指针也

OC内存管理-1

栈区:从高到低分配 堆区:从低到高 BSS段:没有初始化的 数据区: 代码段: OC内存管理方式: 1 MRC 手动内存管理 2 ARC 自动内存管理 nil是给对象赋空值 下个有道云笔记 内存管理 一.总结: 1.只有OC对象才需要内存管理,基本数据类型无效 2.OC对象存放在堆里面 3.非OC对象一般放在栈里面(栈内存会被系统自动回收) 二.引用计数器: 1.每个OC对象都有自己的引用计数器 2.它是一个整数(int) 3.表示有多少人正在使用这个对象 4.每个OC对象都有4个字节的存储空间

OC内存管理(一)

OC内存管理: 前言:为什么基本数据类型分配在栈区,而动态分配的内容在堆区. 因为基本数据类型的存放的数据在内存中得大小是固定的比如int类型的数据就是分配-2^31——2^31-1.而要分配不确定的数据在内存中得话,就动态分配到堆区. 一:基本原理 1>为什么要进行内存管理. 内存管理的范围是:继承自NSObjetc的类对象,对基本数据类型无效 我们知道手机的内存非常有限,而基本数据类型在编译时会静态分配内存在栈区,当代码块结束时,栈区的成员变量自动释放,当然指向对象的指针也会被释放.而对象是

OC内存管理2

这里是新的内容 OC内存管理2,布布扣,bubuko.com

黑马程序员-OC内存管理 @property的增强

涉及到内存管理,只读,多线程等很多功能时,setter和getter方法也就没那么简单了:当然@property依然强大,很好用: 1:内存管理相关参数: *:retain:  (如果是oc对象类型),生成的setter会自动release旧值,retain新值: *:assign:(适用于非oc对象)  这个是默认的值 *:copy:release旧值,copy新值: @property (retain) NSString *name; // 同类型的参数不能同时写 // @property

oc 内存管理小结(**输出才是最好的学习**)

引言 内存管理:清理(回收)不用的内存,以便内存能够再次利用. 这里就需要关注——怎样确定对象不再需要使用,并且其占用的内存可以被收回. 在Xcode4.2发布之前,oc内存管理全靠程序员自己,即手工管理内存计数. 在Xcode4.2版本之后,支持自动引用计数(Automatic Reference Counting,ARC),即摆脱手工管理,程序员从烦恼的内存管理问题中彻底解脱,oyeah~~ 但是,为了理解过去遗留的代码,还是需要了解手工管理内存的原理.并且,也可以帮助coder们更明智地决

OC内存管理相关整理

OC内存管理 一.基本原理 (一)为什么要进行内存管理.内存管理的目的是什么? 由于移动设备的内存极其有限,所以每个APP所占的内存也是有限制的,当app所占用的内存较多时,系统就会发出内存警告,这时需要回收一些不需要再继续使用的内存空间,比如回收一些不再使用的对象和变量等. 管理范围:任何继承NSObject的对象,对其他的基本数据类型无效 管理目的: 1.不要释放或者覆盖还在使用的内存,这会引起程序崩溃: 2.释放不再使用的内存,防止内存泄露.(ios程序的内存资源很是宝贵.) 本质原因是因

OC内存管理详解

前言 由于移动设备的内存有限,所以我们需要对内存进行严格的管理,以避免内存泄露造成资源浪费.在OC中,只有对象才属于内存管理范围,例如int.struce等基本数据类型不存在内存管理的概念.在iOS开发中,对内存的管理实际上就是对引用计数器的管理. OC内存管理的三种方式 自动垃圾收集(Automatic Garbage Collection): 手动引用计数器(Manual Reference Counting)和自动释放池: 自动引用计数器(Automatic Reference Count

OC 内存管理机制总结

OC 内存管理机制总结 一:OC内存管理机制目前分为两块,其一自动内存管理机制,其二手动内存管理机制: 1.首先我们从自动内存管理机制讲起: 1)什么是自动内存管理机制,自动内存管理机制就是程序中所创造的成员变量交由系统统一处理,不需要外部人员干预,有点像java中gc(垃圾回收机制). 2)之前是没有自动内存管理机制的,后期苹果想拓展自己的开发市场,吸引其他平台开发者入住ios开发阵营,其中收到内存管理是很发杂的一块,对于转入IOS开发者不利,因此苹果推出了自动内存管理机制. 2.接下来我们将

OC内存管理总结,清晰明了!

<span style="font-size:18px;">OC内存管理 一.基本原理 (一)为什么要进行内存管理. 由于移动设备的内存极其有限,所以每个APP所占的内存也是有限制的,当app所占用的内存较多时,系统就会发出内存警告,这时需要回收一些不需要再继续使用的内存空间,比如回收一些不再使用的对象和变量等. 管理范围:任何继承NSObject的对象,对其他的基本数据类型无效. 本质原因是因为对象和其他数据类型在系统中的存储空间不一样,其它局部变量主要存放于栈中,而对象