我只是好奇,想知道當一個對象已經alloc
製成,並且爲它分配一塊內存,爲什麼init
不要使用這塊內存,並改變對象的地址?ALLOC +初始化的內存使用機制
NSDate *t = nil;
NSLog(@"t = %p",t); // t = 0x0
t = [NSDate alloc];
NSLog(@"t = %p",t); // t = 0x100107af0
t = [t init];
NSLog(@"t = %p",t); // t = 0x1001035a0
我只是好奇,想知道當一個對象已經alloc
製成,並且爲它分配一塊內存,爲什麼init
不要使用這塊內存,並改變對象的地址?ALLOC +初始化的內存使用機制
NSDate *t = nil;
NSLog(@"t = %p",t); // t = 0x0
t = [NSDate alloc];
NSLog(@"t = %p",t); // t = 0x100107af0
t = [t init];
NSLog(@"t = %p",t); // t = 0x1001035a0
兩步初始化允許我們做這些事情(即替代的類的實例再依賴於所謂的初始化)。遍佈Foundation和UIKit的類集羣利用此優勢來返回針對特定用例進行優化的實例。例如,UIColor
本身只是其實現顏色緩存(所有命名初始化程序如+blackColor
),RGB顏色空間(+colorWithRed:green:blue:alpha
),黑白顏色空間(+colorWithWhite:alpha:
),CIColor
兼容性等的子類的接口。 NSDate
也是。當你撥打-init
時,Apple有辦法和動機返回一個與NSDate
實現相同接口的不同對象作爲優化工具,因爲只要在嘗試發送消息時不發射導彈它正確。
截至最新的iOS SDK,調用[NSDate alloc]
始終返回相同的內存位置。你可以用下面的代碼來驗證此行爲:
NSDate *date1, *date2;
date1 = [NSDate alloc];
NSLog(@"date1: %p", date1);
date1 = [date1 init];
NSLog(@"date1: %p", date1);
date2 = [NSDate alloc];
NSLog(@"date2: %p", date2);
date2 = [date2 init];
NSLog(@"date2: %p", date2);
我懷疑它與事實NSDate
是class cluster做。
如果類集羣的私有子類具有不同的存儲要求,那麼不可能知道內部要分配多少內存。解決這個問題的方法之一就是蘋果使用NSDate
的方法是讓init
和工廠方法處理所有的內存分配,因爲這些方法知道實際將使用哪個私有子類。
在這一點上,所有的alloc
爲你做的是允許用戶保存用於在Objective-C中的任何地方創建對象的模式[[NSDate alloc] init]
。由於alloc
返回的內存位置總是被丟棄,因此alloc
可能只是返回一個固定的內存位置,這正是它所做的。
'NSDate'不發射導彈?我放棄蘋果Google! –