内存管理(二)
ARC
由于采用计数的方式管理内存,所以我们在掌握程序的时候要清楚所有的对象的获得与放弃的实际,实际上是非常的麻烦,于是采用了一种ARC(自动引用计数)这种编译期计数方法,利用它大大简化了内存管理的工作量。它会在编译的期间添加合适的retain/release/autorelease等函数来保证对象正确的释放。
ARC中需要注意的是
禁止调用引用计数相关的函数retain/release/autorelease/retainCount 以及这些函数的selector。
自动释放池
同时又有管理自动释放池的新用法,因为在ARC中禁止使用NSAutoReleasePool。
@aotoreleasepool{
/*可进行系列操作
可使用break、return、goto语法*/
}
同时新方法在非ARC模式下也能进行使用,并且使用的效率更高,因为在NSAutoReleasePool下不能使用跳转语句。
方法族
一共定义有五种方法族(由于ARC允许混合链接手动管理内存和自动管理内存,所以为了能让编译器明确的区分,同对象生成相关的方法集合叫方法族),
- alloc方法族
- copy方法族
- mutableCopy方法族
- new方法族
- init方法族
- 以init开头的方法必须被定义为实例方法,它一定要返回id类型或者父类、子类的指针。
若要由调用端来release一个方法返回的对象,而这个方法又不是以上面关键字开头的,ARC可能不会释放这个对象,从而造成内存的泄露,因此给方法命名的时候必须规范,例如无意中使用new,copy等开头,这些的命名都是不对的,可能会造成错误释放,也可能会在编译的时候提示警告或错误,所以要严格遵守内存管理相关的函数命名规则。
dealloc的定义
ARC编程中不能显示的调用dealloc方法,手动内存管理下除了调用父类的dealloc方法,也不允许显示的调用。ARC有效的时候不允许调用父类的dealloc方法,因为编译器会自动的处理。
循环引用
如果两个对象相互引用的话,形成了循环,一方等待着另一方的释放才释放这样就叫循环引用,会造成内存的泄露。
弱引用
为了避免循环引用,在ARC中引入了弱引用这个概念,只通过储存一个指向对象的指针创建的,不保留对象,在OC中通过_ _weak修饰符来定义弱引用。
_ _weak id example;
弱引用下,无论是对变量赋值还是解除引用,变量的计数都不会变,若没有声明弱引用就是强引用,也可以通过_ _strong实现。强引用和弱引用都会被隐式的初始化为nil。弱引用会在其指向的单例被释放之后自动变成nil,这就是弱引用的自动nil化,也就是弱引用不会形成野指针。
生命周期修饰符
- strong
- _ _weak
- _ _autoreleasing
- 当一个函数有多个返回值的时候通常案通过指针来实现,在OC中叫写回传。
- ARC的编译器会自动为函数的二重指针变量上加上_ _autoreleasing修饰符。
- 根本目的是为了获取一个延迟释放的对象
- _ _unsafe_unretained
- 修饰的变量为非nil化的弱指针,就是若指向的内存区域被释放,这就是个野指针。
- 如同字面上看的一样是unsafe的
*在既不想保持赋值的对象,也不想赋值的对象在释放后自动变为nil后使用。