NSArray alloc和init

时间:2015-05-05 12:48:44

标签: ios objective-c nsarray

我对NSArray初始化感到有些困惑。令人困惑的是我们有不同的init方法来初始化它,如果我只是在不给出任何大小和任何对象的情况下初始化它,编译器如何知道它在RAM中的对象数量或大小。 init方法背后的逻辑/差异是什么?能有人简单解释一下吗?

编辑:

NSArray *sortedArray = [[NSArray alloc] init];
NSSortDescriptor *descriptor = [[NSSortDescriptor alloc]   initWithKey:@"quota" ascending:NO];
NSArray *sortDescriptors = [NSArray arrayWithObject:descriptor];
//How is that possible to modifying to immutable object
sortedArray = [sortedContainers sortedArrayUsingDescriptors:sortDescriptors];

我知道 NSArray NSMutableArray 之间存在差异,而且我没有找到差异。我只是想知道代码如何编译/执行而没有错误。

2 个答案:

答案 0 :(得分:4)

[[NSArray alloc] init]返回一个空的不可变数组。这没什么好奇怪的。你还有什么方法可以从一种方法中回归“没有物品?”

  

编译器如何知道RAM中的对象计数或大小

对象计数为0.它是空的。它在RAM中的大小是空NSArray的大小。 NSArray是一个对象,因此它有一些标准objc_object开销,加上NSArray的一些实例变量。

也就是说,作为一个实现细节,Cocoa优化了这一点,并且总是为所有空NSArray个对象返回相同的单例。您可以通过以下方式证明:

NSArray *a = [[NSArray alloc] init];
NSArray *b = [[NSArray alloc] init];
NSLog(@"%p", a);
NSLog(@"%p", b);
if (a == b) { // Pointer equality, not isEqual:
    NSLog(@"Same object");
}

那么,这是做什么的?

NSArray *sortedArray = [[NSArray alloc] init]; // (1)
// ... code that doesn't matter ...
sortedArray = [sortedContainers sortedArrayUsingDescriptors:sortDescriptors]; // (2)

在第1行,您正在创建一个本地指针变量sortedArray并将其指向一个空数组(它恰好是一个单例,但这是一个优化细节)。

在第2行,您可以通过调用NSArray创建完全不同的sortedArrayUsingDescriptors:。然后,您将sortedArray指向该对象。 ARC看到你不再指向空数组并释放它。 (同样,优化细节会在此处跳转,实际步骤可能会有所不同,但效果会相同。)

这里的正确代码是:

// ... Code that sets up sortDescriptors ...
NSArray *sortedArray = [sortedContainers sortedArrayUsingDescriptors:sortDescriptors]; 

现在,在非常现代的ObjC中,你不会经常看到[[NSArray alloc] init]写出来。编写@[](这实际上只是方法调用的语法糖)更容易。但在将数组文字添加到语言之前,[[NSArray alloc] init][NSArray array]相当普遍。

答案 1 :(得分:0)

如果您只是初始化NSArray而没有给出任何大小和任何对象,它将在生命周期内保持为空。 NSArray是不可变的

如果您的问题与NSMutableArray有关,请阅读here at the SO