• 小小ARC造福无数码农


    今天无意中看到非常久之前的一个项目,古老的语法规范,还有更让人战战兢兢“内存管理代码”!

    在这不得不说OC中内存管理的三种分类:

    • Mannul Reference Counting(MRC,手动管理,在开发iOS5.0之前的版本号的项目时我们要自己负责使用引用计数来管理内存,比方要手动retain、release、autorelease 等,而在其后的版本号能够使用ARC,让系统自己管理内存。

      )

    • Automatic Reference Counting(ARC,自己主动引用计数,iOS5.0 之后推出的)

    • Garbage Collection(垃圾回收)。

      iOS不支持垃圾回收; ARC作为苹果新 供的技术,苹果推荐开发人员使用ARC技术来管理内存;

      那么今天就着重探讨一下ARC!!!

      1、什么是ARC?

        Automatic Reference Counting,自己主动引用计数,即ARC,能够说是WWDC2011和iOS5所引入 的最大的变革和最激动人心的变化。ARC是新的LLVM 3.0编译器的一项特性,使用ARC,能够说一举攻克了广大iOS开发人员所憎恨的手动内存管理的麻烦。

        在project中使用ARC很easy:仅仅须要像往常那样编写代码,仅仅只是永远不写retain,release和 autorelease三个keyword就好,这是ARC的基本原则。

        当ARC开启时,编译器将自己主动在代码合适的地方插入retain, release和autorelease,而作为开发人员,全然不须要操心编译器会做错(除非开发人员自己错用ARC了)。

        手动管理内存, 能够简称MRC (Manual Reference Counting)   

        ARC与其它语言的”垃圾回收”机制不同。
        ARC:编译器特性
        “垃圾回收”:执行时特性

      2、ARC工作原理及推断准则

        ARC是Objective-C编译器的特性,而不是执行时特性或者垃圾回收机制,ARC所做的仅仅只是是在代码编译时为你自己主动在合适的位置插入release或autorelease

      ARC的对象回收推断准则:

      仅仅要没有强指针指向对象,对象就会被释放。

      注意:当使用ARC的时候,临时忘记“引用计数器”,由于推断标准变了。

      3、指针分类

      1) 强指针:默认的情况下,全部的指针都是强指针,keyword__strong
      2) 弱指针:__weakkeyword修饰的指针

      声明一个弱指针例如以下: 

      __weak Person *p;
      

      4、ARC机制图解

      NSString *firstName = @"OneV";
      

      这个时候firstName持有了@"OneV"。



        当然,一个对象能够拥有不止一个的持有者(这个类似MRC中的retainCount>1的情况)。

      在这个样例中显然self.textField.text也是@“OneV",那么如今有两个指针指向对象@"OneV”(被持有两次,retainCount=2,事实上对NSString对象说retainCount是有问题的,只是anyway~就这个意思而已.)。   过了一会儿,或许用户在textField里输入了其它的东西,那么self.textField.text指针显然如今指向了别的字符串,比方@“onevcat",可是这时候原来的对象已然是存在的,由于另一个指针firstName持有它。
      如今指针的指向关系是这种:

        仅仅有当firstName也被设定了新的值,或者是超出了作用范围的空间(比方它是局部变量可是这个 方法运行完了或者它是实例变量可是这个实例被销毁了),那么此时firstName也不再持有 @“OneV",此时不再有指针指向@"OneV",在ARC下这样的状况发生后对象@"OneV"即被销毁,内存释放。   
        类似于firstName和self.textField.text这种指针使用keywordstrong进行标志,它意味着仅仅要该指针指向某个对象,那么这个对象就不会被销毁。

      反过来说,ARC的一个基本规则即是,仅仅要某个对象被任一strong指针指向,那么它将不会被销毁。假设对象没有被不论什么strong指针指向,那么就将被销毁。
        在默认情况下,全部的实例变量和局部变量都是strong类型的。能够说strong类型的指针在行为上和MRC时代retain的property是比較相似的。 

        既然有strong,那肯定有weak咯~,weak类型的指针也能够指向对象,可是并不会持有该对象。
        比方:

        __weak NSString *weakName = self.textField.text
      

      得到的指向关系是:

        这里声明了一个weak的指针weakName,它并不持有@“onevcat"。假设self.textField.text的内容发生改变的话,依据之前提到的"仅仅要某个对象被任一strong指针指向,那么它将不会被销毁。假设对象没有被不论什么strong指针指向,那么就将被销毁”原则,此时指向@“onevcat"的指针中没 有strong类型的指针,@"onevcat"将被销毁。

        同一时候,在ARC机制作用下,全部指向这个对象的weak指针将被置为nil。这个特性相当实用,相信无数的开发人员都以前被指针指向已释放对象所造成的EXC_BAD_ACCESS困扰过,使用ARC以后,不论是strong还是weak类型的指针,都不再会指向一个dealloced的对象,从根源上攻克了意外释放导致的crash。

        只是在大部分情况下,weak类型的指针可能并不会非经常常使用。比較常见的使用方法是在两个对象间存在包括关系时:对象1有一个strong指针指向对象2,并持有它,而对象2中仅仅有一个weak指针指回对象1,从而避免了循环持有。

        一个常见的样例就是oc中常见的delegate设计模式,viewController中有一个strong指针指向它所负责管理的UITableView,而UITableView中的dataSource和delegate指针都是指向viewController的weak指针。

      能够说,weak指针的行为和MRC时代的assign有一些相似点,可是考虑到weak指针更聪明些(会自己主动指向nil),因此还是有所不同的。 


      通过上面的图解。大家一定对ARC底层的处理机制有更深的认识了吧!

      欢迎大家提出补充哦。

  • 相关阅读:
    游标cursor
    SQL: EXISTS
    LeetCode Reverse Integer
    LeetCode Same Tree
    LeetCode Maximum Depth of Binary Tree
    LeetCode 3Sum Closest
    LeetCode Linked List Cycle
    LeetCode Best Time to Buy and Sell Stock II
    LeetCode Balanced Binary Tree
    LeetCode Validate Binary Search Tree
  • 原文地址:https://www.cnblogs.com/llguanli/p/7168694.html
Copyright © 2020-2023  润新知