autoreleasepool 自動釋放池的理解

常見的面試題:如下代碼存在什麼樣的問題?應該如何改進?面試

 

    for (int i = 0; i < 100000; i++) {oop

            NSString *str = @"abc";spa

            str = [str stringByAppendingString:@"xyz"];對象

    }blog

 

利用leaks查看內存泄漏狀況內存

 

 

可知:NSString對象str並無立刻被釋放,在內存中會同時存在100000個NSString對象,形成內存急增,等100000for循環結束才釋放作用域

改進:string

    for (int i = 0; i < 100000; i++) {for循環

        @autoreleasepool {table

            NSString *str = @"abc";

            str = [str stringByAppendingString:@"xyz"];

        }

    }

 

或者(注意NSAutoreleasePool ARC下不可用,必須將工程改成MRC)

 

    for (int i = 0; i < 100000; i++) {

        //建立一個自動釋放池

        NSAutoreleasePool *pool = [NSAutoreleasePool new];

        NSString *str = @"abc";

        str = [str stringByAppendingString:@"xyz"];

        //自動釋放池被銷燬或耗盡,會向自動釋放池中的全部對象發送release消息

        [pool drain];

    }

 

利用leaks查看內存泄漏狀況

 

 

可知:不會形成內存急增,每次for循環結束NSString對象str都會釋放,在內存中會只存在1個NSString對象str

 

自動釋放池(autoreleasepool)的工做原理:

    //@autoreleasepool {}中的代碼

    void *context = objc_autoreleasePoolPush();

    //當前runloop迭代結束時進行pop操做

    objc_autoreleasePoolPop(context);

 

autoreleasepool是個棧結構,對象加入池子時其實質是進行入棧Push操做,釋放對象時其實質是進行出棧Pop操做。

 

標記爲autorelease的對象在出了做用域範圍後,會被添加到最近一次建立的自動釋放池中,當前runloop迭代結束時,會向自動釋放池中的全部對象發送release消息,當池子裏的全部對象引用計數都爲0

時該池子被銷燬

相關文章
相關標籤/搜索