ARC 學習筆記(三)

引用計數的原則

  1. 自己生成的對象自己持有
  2. 非自己生成的對象自己也可以持有
  3. 不再需要自己持有的對象時釋放
  4. 非自己持有的對象無法釋放

案例:

/*
    * 自己生成並持有對象
    */

    id obj1 = [[NSObject alloc] init];

    /*
    * 自己持有對象
    */

    [obj1 release];

    /*
    * 釋放對象
針仍然被保留在變量obj1中
    * 但對象一經釋放絕對不能被訪問
    * /



    /*
    * 取得非自己生成的對象
    */

    id obj2 = [NSMutableArray array];

    /*
    * 自己不持有對象
    */

    [obj2 retain];    //ARC不需要這個操作,編譯器會自動幫我們實現。而MRC下需要。

    /*
    * 自己持有對象
    */

    [obj2 release];

    /*
    * 釋放對象
    */

那麼[NSMutableArray array]這個方法是如何實現取得對象存在,而不持有對象的呢。其實是用到了autorelease方法。

-(id) object {
    id obj = [[NSObject alloc] init];

    [obj autorelease];

    return obj;
}

autorelease與release的區別在於。release一個對象,該對象立馬釋放,而autorelease一個對象,該對象註冊到autoreleasepool中,pool結束時自動調用release。

- (id) autorelease {
    [NSAutoreleasePool addObject:self];
}

因此上面的代碼可以如下表示

NSAutoreleasePool *pool = [[NSAutoReleasePool alloc]init];  

id obj = [[NSObject alloc] init];

[obj autorelease];

[pool drain];   

autoreleasepool是跟NSRunLoop聯繫在一起的。NSRunLoop每次循環過程中NSAutoreleasePool對象被生成或被廢棄。
另外還有一點就是當有大量的autorelease對象生成,而沒有被釋放時,就會造成內存不足。比如

for (int i = 0; i < 圖象數; ++i) {
    /*
    * 讀入大量圖像
    * 大量產生autoreleae對象
    * 沒有釋放造成內存不足
    * /
}

解決方案就是在適當的地方自己生成、持有、廢棄autoreleasepool對象

for (int i = 0; i < 圖象數; ++i) {

    NSAutoreleasePool *pool = [[NSAutoReleasePool alloc]init];  
    /*
    * 讀入大量圖像
    * 大量產生autoreleae對象
    * /

    [pool drain];

    /*
    * autorelease對象被釋放
    */
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章