关闭

iOS中内存初级管理

标签: ios
234人阅读 评论(0) 收藏 举报
分类:

   

   1:内存的管理方式

     在ios中可能会遇见(MRC)和(ARC)的两种管理方式.

     MRC:使用的人群可能是一些老程序员,应为他们觉得比arc更安全好用.(⼈人⼯工引⽤用计数)

 ARC:是基于MRC的一种管理方式(⾃自动引⽤用计数)


OC采⽤用引⽤用计数机制管理内存,当⼀一个新的引⽤用指向对象时,引⽤用计数器就递增,当去掉⼀一个引⽤用时,引⽤用计数就递减当引⽤用计数到零时,该对象就将释放占有的资源


   2:影响内存计数的方法

       下面以一个person类为演示基础

 2.1 +alloc  (引用计数加1)

 开辟内存空间,让被开辟的内存空间的引⽤用计数变为1。这是由01的过程

代码实现:

Person *p = [[Person alloc] init];
    
    NSLog(@"%ld",[p retainCount]);
这是的输出结果为:1

2.2 -retain (引用计数加1)
如果内存空间之前引用计数为1,retain变为2

代码如下

 Person *p = [[Person alloc] init];
    
    Person *p2 = [p retain];
    NSLog(@"%ld",[p retainCount]);

输出结果为:2

2.3 -copy 把某一内存区域的内容拷贝一份,拷贝到新的内存空间中,被拷贝的区域的引用计数不变,新内存区域的引用计数为1

Person *p = [[Person alloc] init];
    
    Person *p2 = [p retain];
    
    Person *p3 = [p2 copy];
    
    NSLog(@"%ld",[p retainCount]);

此时的输出结果为:2

2.4 -release (引用计数减1)   如果之前的引用计数为1,release之后变为0,内存会被系统回收.

Person *p = [[Person alloc] init];
    
    Person *p2 = [p retain];
    
    Person *p3 = [p2 copy];
    
    [p release];
    
    NSLog(@"%ld",[p retainCount]);

输出结果为:1

 2.5 -dealloc 当引用计数为0的时候,由对象自动调用

调试方法

2.5.1 首先在对应类的.m文件中写上

-(void)dealloc
{
    NSLog(@"引用计数为0,系统自动调用");
    [super dealloc];
}

然后在main.m中调用

Person *p = [[Person alloc] init];
    
    Person *p2 = [p retain];
    
    Person *p3 = [p2 copy];
    
    [p release];
    [p release];
    
    NSLog(@"%ld",[p retainCount]);

应为在第一次使用 p release是p的应用计数为2,所有用两次release才能吧引用计数调成0,才能出现效果


2.6 -autorelease,未来的某一时刻引用计数减1


在autorelease中所有的引用都是在栈区存放,所以在调用的时候返回的结果是,先进后出,后进先出



3:内存管理原则

引用计数和增加相等,当引用计数为0的时候,该快内存则不再被使用.

在一块代码内,增加和减少的次数要相等.


  4:Copy的实现

  在实现copy的时候有两种过程,一个是深拷贝和浅拷贝

4.1浅拷贝

  如果指针*p指向了A内存的a地址,*p2也指向了A内存中的a地址,两个指向同一个地址,如果*p指向的内容改变,则*p2也改变.

©代码如下:在实现copy动作的时候用实现协议<nscopying>

©在对应类的.m文件中实现该方法

- (id)copyWithZone:(NSZone *)zone
{
    //浅拷贝
    return [self retain];

}

4.2深拷贝   在原有的基础上把对用的区域拷贝到另外一块内存中

实现代码如下 先实现协议<nscopying>

在对应.m文件中实现如下方法,(比较单一的)

- (id)copyWithZone:(NSZone *)zone
{
  
    //深拷贝
    //申请空间,创建一个对象
    Person *p = [Person allocWithZone:zone];
    //进行赋值
    p.name = self.name;
    p.age = self.age;
    p.sex = self.sex;
    //3返回刚刚生成的对象
    
    return  p;
    
    
}
在main.m中调用如下

  //深拷贝
    Teacher *teacs = [[Teacher alloc] init];
    
    
    teacs.name = @"gggggggggggggg";
    
    Teacher *t2 = [teacs copy];
    
    teacs.name = @"dddddd";
    NSLog(@"-------=%@",t2.name);
    
    NSLog(@"-------=%ld",[t2 retainCount]);
运行结果如下


综上可见,程序在执行深度拷贝的时候,不会改变copy后对象的数值.


0
0

猜你在找
【直播】机器学习&数据挖掘7周实训--韦玮
【套餐】系统集成项目管理工程师顺利通关--徐朋
【直播】3小时掌握Docker最佳实战-徐西宁
【套餐】机器学习系列套餐(算法+实战)--唐宇迪
【直播】计算机视觉原理及实战--屈教授
【套餐】微信订阅号+服务号Java版 v2.0--翟东平
【直播】机器学习之矩阵--黄博士
【套餐】微信订阅号+服务号Java版 v2.0--翟东平
【直播】机器学习之凸优化--马博士
【套餐】Javascript 设计模式实战--曾亮
查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:61669次
    • 积分:1578
    • 等级:
    • 排名:千里之外
    • 原创:98篇
    • 转载:6篇
    • 译文:0篇
    • 评论:1条
    最新评论