//
// main.m
// OCStudy
//
// Created by LiuMingchuan on 15/9/24.
// Copyright © 2015年 LMC. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Person.h"
#import "Dog.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *person = [[[Person alloc]init]autorelease];
}
return 0;
}
autorelease并不是自动释放某个对象
上面的代码可以看出,调用autorelease之后会返回对象本身
调用玩autorelease之后,对象的引用计数并不会改变
autorelease会将对象扔到一个自动释放池中,当自动释放吃销毁的时候,释放池中的每一个对象都会调用release方法
我们看到上边的@autoreleasepool它就是一个自动释放池,前大括号是新建了一个释放池,后大括号之后代表自动释放吃的销毁
通过设置断点(@autoreleasepool的后大括号),我们可以看到通过断点之后,打印了一下信息
几个小错误示例:
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *person = [[[Person alloc]init]autorelease];
[person release];//person引用计数-1,-->0
}//自动释放池销毁,会再次调用person的release,造成野指针错误
return 0;
}
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *person = [[[[Person alloc]init]autorelease]autorelease];//两次autorelease
}//释放池销毁,因为调用了两次autorelease,所以销毁时会调用两次person的release,同样造成野指针错误
return 0;
}
我们必须遵循一个alloc对用一个release或者autorelease,上面的写法都未遵循这样的法则,所以出现野指针错误
autorelease的作用:
不用关心对象的释放时间,不用关心对象什么时候调用release方法
autorelease注意点:
占用内存比较大的对象,不要随便使用autorelease,因为无法控制对象的释放时间;即便是占用内存较小的对象使用autorelease,也会效率产生一定的影响
在iOS的运行过程中,会创建无数个释放池,用户的交互可能就会创建释放池,这些释放池是以栈的形式存在的(先进后出),当我们的一个对象调用autorelease时,会将对象放到栈中最顶端的释放池中!
ios5.0之前的自动释放吃创建和销毁
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc]init];
Person *person = [[[Person alloc]init]autorelease];
[pool release];
ios5.0之后的创建和销毁
@autoreleasepool {
Person *person = [[[Person alloc]init]autorelease];
}