黑马程序员_MRC2

MRC

上次blog我谈到iOS MRC内存管理的原理、原则以及出现的问题,接下来我会结合实例继续介绍在处理MRC内存管理的时候经常出现的问题:内存泄露、循环引用(retain)

一、内存泄露:

内存泄露的主要原因在于,没有遵守内存管理的原则,要么忘记release,要么release的次数少了。下面通过代码展示:

<span style="font-family:Comic Sans MS;font-size:18px;">//第一种情况
#import <Foundation/Foundation.h>
#import "Person.h"
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        //创建car对象
        Car *car=[Car new];
    }
    return 0;
}</span>
分析:指针变量car存在栈区,是一个临时变量,在程序执行到其作用域({})外时会自动销毁。但是,在堆区的对象需要手动回收,而指向这片内存的指针已经被销毁,我们在这个程序结束以前,是没有办法回收该对象的内存的。这就造成了内存泄露。

<span style="font-family:Comic Sans MS;font-size:18px;"><span style="color:#000066;">//第二种情况
#import <Foundation/Foundation.h>
#import "Person.h"
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        //创建car对象
        Car *car=[Car new];
        car=nil;
        [car release];
    }
    return 0;
}</span></span>
分析:指针变量car被重设为nil,但堆区内存并没有释放,我们也无法再次获得该对象的内存地址,造成内存泄露。

<span style="font-size:18px;">//第三种情况
#import <Foundation/Foundation.h>
#import "Person.h"
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        //创建car对象
        Car *car=[Car new];
        [car retain];
        [car release];
    }
    return 0;
}</span>

分析:对象被retain了一次或多次,但只是release了一次或少次,在出了指针的作用域后,对象无法释放。
:对象被retain了,有时候并没有这么明显,可能在调用函数的时候被retain或copy等。

对于内存泄露,并没有一劳永逸的方法,只能靠自己的写代码的时候,多加注意,严格遵循内存管理的原则。

二、循环retain

 循环引用是一个很经典的问题,我以前在学c++的时候,就遇到过,C++通过强弱指针解决这个问题,当然本质上C++的智能指针也是通过引用计数解决问题。下面我通过一个实例来看一下OC在MRC模式下如何处理这个问题。

//main.m
#import <Foundation/Foundation.h>
#import "Person.h"
#import "Dog.h"
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        //创建人对象
        Person *lele=[Person new];
        //创建狗对象
        Dog *wangcai=[Dog new];
        //将人的狗设为 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值