Objective-C中的alloc和init問題

從開始學的NSString *name=[[NSString alloc] init] 起,僅僅這句話是分配內存空間,一直在用,歷來沒考慮過它的內部是怎麼實現的。今天無心中看到了這一句代碼:微信

NSString *name = [NSString alloc];
NSLog(@"%p",name);
name = [name init];
NSLog(@"%p",name);

試着打印了一下,發現兩個的內存地址不同:spa

 

alloc是開闢一個內存空間,init是初始化,爲何初始化不在原有的內存空間上初始化,而是從新開闢一個內存空間。因而開始查資料,這時又發現了一個新的迷惑:指針

NSObject *obj = [NSObject alloc];
NSLog(@"%p",obj);
obj = [obj init];
NSLog(@"%p",obj);

打印結果:code

怎麼地址又變同樣了?再打印NSArray的試一試:對象

NSArray *person = [NSArray alloc];
NSLog(@"%p",person);
person = [person init];
NSLog(@"%p",person);

再次打印結果:blog

仍然是不同的。緣由是什麼呢?首先看看NSStrng的init方法吧:內存

-(id)init{
    if(self = [super init])  {// 從新賦值
        //
    }
}

從代碼中能夠分析,self=[super init]若是不爲nil,就從新分配內存空間,這就解釋了爲何 NSString,NSArray的調用alloc]init]方法後,內存地址會不同,可是NSObject爲何會同樣呢,咱們知道NSObject是一切類的基類,當[[NSString alloc]init]執行時,調用的[super init]就是 NSObject中的init方法,既然NSObject身爲基類,它也就沒法調用super init,因此當NSObject執行[[NSObject alloc]init]時,也就沒有了init從新分配空間這一環節。it

至於蘋果公司爲何初始化一個實例要分兩步,我的認爲是方便構造後初始化不一樣的方法,若是用 new關鍵字,只能調用一個init,而不能調用initWithName等方法。class

知識拓展:程序

NSString  alloc以後,沒有init,那麼這部分alloc後的內存空間可不能夠用?答案是顯而易見的,若是能夠用,蘋果公司也就不必提供一個init方法,那麼alloc後的指針稱爲何呢? 懸掛指針。 

若是一個地方指針既不爲空,也沒有被設置爲指向一個已知的對象,則這樣的指針稱爲懸掛指針。在程序裏面是很危險的事。當程序運行使用該指針時,程序不能判斷指針的合法性,將會產生很嚴重的錯誤。

 

【掃描關注更多精彩內容】

微信公衆號:xiaoniu

相關文章
相關標籤/搜索