三、Object-C ARC和弱引用

作者: Yink_Liu | 来源:发表于2018-07-06 21:03 被阅读14次

    Objective-C学习索引

    一、ARC自动引用计数

    1、ARC通过在编译期间自动添加合适的realese/retain/autorelease等函数,来确保对象被正确的释放。
    2、ARC只能管理OC的对象,不能管理通过malloc申请的内存。
    3、ARC模式下不能调用realese/retain/autorelease这些方法。
    4、ARC中,未指定初始值的变量都会被初始化为nil。
    5、alloc、copy、mutableCopy、new为开头的方法(即方法族)表示调用者对被创建对象拥有所有权,返回的对象必须是可以被retarin的。
    init方法族必须被定义为实例方法,它一定哟啊返回instencetype、id、父类或子类的指针,除了init的方法族,其它方法族可以是类方法也可以是实例方法。
    命名时不能误用这些关键字,否则可能造成ARC误释放!!!
    6、不要在dealloc中释放实例变量(但可以释放资源),也不要调用[super dealloc]ARC下回自动调用。

    二、弱引用

    2.1 循环引用

    @implementation Person{
        id _friend;
    }
    - (void)setFriend:(id) obj{
        _friend = obj;
    }
    
    Person * p1 = [[Person alloc] init];
    Person * p2 = [[Person alloc] init];
    [p1 setFriend:p2];
    [p2 setFriend:p1];
    

    A拥有B,B拥有A,ARC时这样写就会出现问题,因为你要释放A,先要等待B释放 反过来,你要释放B,又要等待A释放。循环。这就叫循环引用。于是造成内存泄漏

    2.2 弱引用

    变量默认定义都是强引用,为了解决循环引用的问题,OC引入弱引用概念
    弱引用,能够引用对象,不会成为对象的所有者。
    __weak Person * p1; // 弱引用
    __strong Person * p2; // 强引用,__strong可以省略,默认强引用

    2.3 自动nil化弱引用

    弱引用会在其指向的实例对象被释放后自动变成nil。即使弱引用指向的对象偶然释放了,弱引用也不会变成野指针。

    @implementation Person{
        __weak id _friend;
    }
    - (void)setFriend:(id) obj{
        _friend = obj;
    }
    
    Person * p1 = [[Person alloc] init];
    Person * p2 = [[Person alloc] init];
    [p1 setFriend:p2];
    [p2 setFriend:p1];
    

    这样写就不会避免了循环引用。因为friend只是弱引用,只引用了对象。
    接着再执行一句如下代码:
    p1 = nil;
    此时p1被释放,弱引用自动变成了nil此时就是:
    p1为nill,p1中的friend弱引用自动释放
    p2还存在,p2中的friend弱引用由于p1的释放,自动变为nill,不会变成野指针。

    所以使用ARC时,应该尽量保证对象之间的关系呈树形结构。而不是环路。
    循环引用时可以采用弱引用,或者手动赋值一方为nil,打破循环关系。

    OC和C语言一起使用的时候,ARC还有一些注意事项,这里只就提一下
    1、C数组保存OC对象,二重指针使用。有时候要用__strong
    2、ARC下不可在C中的结构体定义或引用OC对象

    相关文章

      网友评论

        本文标题:三、Object-C ARC和弱引用

        本文链接:https://www.haomeiwen.com/subject/wlabuftx.html