参考文献: iOS ARC 完全指南
提示本文中所说的"实例变量"即是"成员变量""局部变量"即是"本地变量"
一、简介
ARC是自iOS 5之后增加的新特性完全消除了手动管理内存的烦琐编译器会自动在适当的地方插入适当的retain、release、autorelease语句。你不再需要担心内存管理,因为编译器为你处理了一切
注意ARC 是编译器特性而不是 iOS 运行时特性(除了weak指针系统)它也不是类似于其它语言中的垃圾收集器。因此 ARC 和手动内存管理性能是一样的有时还能更加快速因为编译器还可以执行某些优化
二、原理
ARC 的规则非常简单只要还有一个变量指向对象对象就会保持在内存中。当指针指向新值,或者指针不再存在时,相关联的对象就会自动释放。这条规则对于实例变量、synthesize属性、局部变量都是适用的
三、strong指针
控制器中有个文本输入框框属性
@property (nonatomic, assign) IBOutlet UITextField *nameField;
1.如果用户在文本框中输入mj这个字符串
那么就可以说nameField的text属性是NSString对象的指针也就是拥有者该对象保存了文本输入框的内容
2.如果执行了如下代码
NSString *name = self.nameField.text;
3.随后用户改变了输入框的内容比如
此时nameFeild的text属性就指向了新的NSString对象。但原来的NSString对象仍然还有一个所有者(name变量)因此会继续保留在内存中
4.当name变量获得新值,或者不再存在时(如局部变量方法返回时、实例变量对象释放时),原先的NSString对象就不再拥有任何所有者,retain计数降为0,这时对象会被释放
如给name变量赋予一个新值
name = @"Jake";
我们称name和nameField.text指针为"Strong指针"因为它们能够保持对象的生命。默认所有实例变量和局部变量都是Strong指针
四、weak指针
weak型的指针变量仍然可以指向一个对象但不属于对象的拥有者
1.执行下面的代码
__weak NSString *name = self.nameField.text;
name变量和nameField.text属性都指向同一个NSString对象,但name不是拥有者
2.如果文本框的内容发生变化,则原先的NSString对象就没有拥有者,会被释放,此时name变量会自动变成nil,称为空指针
weak型的指针变量自动变为nil是非常方便的这样阻止了weak指针继续指向已释放对象避免了野指针的产生不然会导致非常难于寻找的Bug空指针消除了类似的问题
3.weak指针主要用于“父-子”关系父亲拥有一个儿子的strong指针因此父亲是儿子的所有者但为了阻止所有权循环,儿子需要使用weak指针指向父亲。典型例子是delegate模式,你的ViewController通过strong指针self.view拥有一个UITableView, UITableView的dataSource和delegate都是weak指针,指向你的ViewController
五、strong和weak指针的使用注意
1.下面代码是有问题的:
__weak NSString *str = [[NSString alloc] initWithFormat:@"1234"];
NSLog(@"%@", str); // 打印出来是"(null)"
2.一般的指针变量默认就是strong类型的,因此一般我们对于strong变量不加__strong修饰,以下两行代码是等价的:
NSString *name = self.nameField.text;
__strong NSString *name = self.nameField.text;
3.属性可以是strong或weak,写法如下
@property (nonatomic, strong) NSString *name;
@property (nonatomic, weak) id delegate;
id obj = [array objectAtIndex:0];
[array removeObjectAtIndex:0];
NSLog(@"%@", obj);
六、ARC小结
1.有了ARC,我们的代码可以清晰很多,你不再需要考虑什么时候retain或release对象。唯一需要考虑的是对象之间的关联,也就是哪个对象拥有哪个对象?
2.ARC也有一些限制
1> 首先ARC只能工作于Objective-C对象,如果应用使用了Core Foundation或malloc()/free(),此时还是需要你来手动管理内存
2> 此外ARC还有其它一些更为严格的语言规则,以确保ARC能够正常地工作
3.虽然ARC管理了retain和release,但并不表示你完全不需要关心内存管理的问题。因为strong指针会保持对象的生命,某些情况下你仍然需要手动设置这些指针为nil,否则可能导致应用内存不足。无论何时你创建一个新对象时,都需要考虑谁拥有该对象,以及这个对象需要存活多久
4.ARC还能很好地结合C++使用,这对游戏开发是非常有帮助的。对于iOS 4,ARC有一点点限制(不支持weak指针),但也没太大关系
七、ARC使用注意总结
原文:http://520119.blog.51cto.com/510119/1411165