我们在程序当中,必须能够聪明地去使用内存。特别是在移动平台上,我们要尽量避免程序无谓地去占有系统内存。
Objective-c中,有很好地内存管理机制,即引用计数(reference count),用来管理内存。当然,现在由于ARC(Automatic Reference Counting)地使用,在很多情况下,我们不用去再进行retain/release等内存管理,但是了解objective-c的内存机制仍然很重要
1. 自动释放池(AutoReleasePool)
自动释放池用来跟踪程序当中创建的对象,当在释放pool的时候,释放这些对象。
NSAutoreleasePool* pool = [[NSAutoreleasePoolalloc]init];//创建自动释放池
[pooldrain]; //释放自动释放池
[object autorelease];//将对象objective添加到自动释放池中
2.引用计数(Reference Count)
首先,我们思考为什么会有引用计数的工作原理。我们在程序中,通过alloc来为对象进行内存分配。而程序在运行中时,可能会有多个位置引用某个我们创建的对象(例如在数组中添加了这个对象),我们必须要确定在使用该对象的每个人都使用完之后,才能释放掉这个对象占用的内存空间。所以我们采用引用计数来记录下引用当前对象的位置的数目,这样当只要因为计数不为0时,那么程序就不会释放掉这个对象的内存。
语句:
alloc:创建对象,分配内存空间,将其引用计数设为1
copy:复制对象,同时设置新对象的引用计数为1
retain;引用计数+1
添加到任何的集合类:引用计数+1
release:引用计数-1
autorelease:将对象添加到自动释放池,但不释放,在之后进行释放
dealloc:释放这个对象占用的内存(我们不会显式调用)
我们将对象添加到任何类型的集合中时,将其引用计数+1;这样是为了当我们在之后对这个对象进行release的时候,集合当中仍保留着对该对象有效的引用。
int main(int argc,const char * argv[])
{
@autoreleasepool {
NSMutableArray* array = [NSMutableArrayarray];
NSMutableString* str1 = [[NSMutableStringalloc]initWithString:@"it's str1"];//用alloc进行创建
NSLog(@"the retain count is %lx",[str1retainCount]);
[arrayaddObject:str1];//添加到array数组中
NSLog(@"after added to array is %lx",[str1retainCount]);
[str1retain]; //retain
NSLog(@"after retain is %lx",[str1retainCount]);
[str1release]; //release
NSLog(@"after release is %lx",[str1retainCount]);
[arrayremoveAllObjects];//移除该对象
NSLog(@"after removed from array is %lx",[str1retainCount]);
[str1release]; //再次release
NSLog(@"last is %lx",[str1retainCount]);
}
return 0;
}
输出为the retain count is 1
after added to array is 2
after retain is 3
after release is 2
after removed from array is 1
last is fffffffffffffff
根据这个例子,应该就对引用计数的整体方法有了掌握。另外[str1 retainCount]这个方法不推荐使用,具体情况可以到http://whentouseretaincount.com查看,里面最醒目的一个词,never永远都不要使用这个方法。
3. 引用计数(reference count)和实例变量(instance variable)
a.
-(void)setName:(NSString *)theName{
name = theName;
}
-(void)setName:(NSString *)theName{
[name release];
name = [[NSStringalloc]initWithString:theName];
}