数组 (NSArray) 用于表示有序的对象列表。只要求每个项目都是 Objective-C 对象;不要求每个对象都是同一个类的实例。
如果要保持数组中的顺序,每个元素都应储存在从 0 开始的索引中。
创建数组
与本章前文所述的值类一样,您可以通过分配和初始化、类工厂方法或数组字面常量来创建数组。
根据对象数量的不同,可用的初始化和工厂方法也多种多样。
+ (id)arrayWithObject:(id)anObject; + (id)arrayWithObjects:(id)firstObject, ...; - (id)initWithObjects:(id)firstObject, ...;
由于 arrayWithObjects: 和 initWithObjects: 方法都采用了以 nil 结束且数量可变的参数,所以您必须包括 nil 并将其作为最后一个值。
NSArray *someArray = [NSArray arrayWithObjects:someObject, someString, someNumber, someValue, nil];
此示例会创建一个如上文所示的数组。第一个对象 someObject 的数组索引为 0;最后一个对象 someValue的索引则为 3。
如果所提供的其中一个值为 nil ,则有可能使项目列表意外截断。
id firstObject = @"someString"; id secondObject = nil; id thirdObject = @"anotherString"; NSArray *someArray =
[NSArray arrayWithObjects:firstObject, secondObject, thirdObject, nil];
在这种情况下,someArray 只会包含 firstObject,因为 secondObject(即 nil)会被解析为项目列表的末尾。
使用紧凑语法创建数组字面常量也是有可能的。
NSArray *someArray = @[firstObject, secondObject, thirdObject];
使用此语法时,请勿使用 nil 来结束对象列表;实际上,nil 是无效值。例如,如果您尝试执行以下代码,那么会在运行时中捕获到一个异常:
id firstObject = @"someString"; id secondObject = nil; NSArray *someArray = @[firstObject, secondObject]; // exception: "attempt to insert nil object"
查询数组对象
创建数组后,可以通过查询来获得信息,如其中有多少个对象,或者其中是否包含给定的项目。
NSUInteger numberOfItems = [someArray count];
if ([someArray containsObject:someString]) { ...
}
还可以按照给定索引查询数组来找到项目。如果请求的索引无效,那么会在运行时中获得越界异常。为了避免得到异常,应始终首先检查项目的数量。
if ([someArray count] > 0) { NSLog(@"First item is: %@", [someArray objectAtIndex:0]);
}
此示例用于检查项目的数量是否大于 0。如果数量大于 0,Foundation 函数 NSLog 会记录第一个项目(索引为 0)的描述。
除了使用 objectAtIndex: 之外,还可以使用下标语法来查询数组,就像在标准的 C 数组中访问值一样。上一个示例可被重写为:
if ([someArray count] > 0) { NSLog(@"First item is: %@", someArray[0]);
}
排序数组对象
NSArray 类提供了多种方法对其收集的对象进行排序。由于 NSArray 是不可变的,因此这类方法都会返回新的数组,并在其中包含排好序的项目。
例如,您可以通过在每个字符串上调用 compare:,对字符串数组进行排序。
NSArray *unsortedStrings = @[@"gammaString", @"alphaString", @"betaString"]; NSArray *sortedStrings =
[unsortedStrings sortedArrayUsingSelector:@selector(compare:)];
可变性
虽然 NSArray 类本身不可变,但它仍可包含可变对象。例如,如果将可变字符串添加到不可变的数组,如下所示:
NSMutableString *mutableString = [NSMutableString stringWithString:@"Hello"]; NSArray *immutableArray = @[mutableString];
就可让您变异该字符串。
if ([immutableArray count] > 0) { id string = immutableArray[0]; if ([string isKindOfClass:[NSMutableString class]]) {
[string appendString:@" World!"]; }
}
如果要在初始创建数组后添加或移除对象,可使用 NSMutableArray,它提供了很多方法来添加、移除或替换一个或多个对象。
NSMutableArray *mutableArray = [NSMutableArray array]; [mutableArray addObject:@"gamma"]; [mutableArray addObject:@"alpha"]; [mutableArray addObject:@"beta"];
[mutableArray replaceObjectAtIndex:0 withObject:@"epsilon"];
此示例创建了由对象 @"epsilon"、@"alpha" 和 @"beta" 构成的数组。还可以对可变数组进行适当排序,而无需创建二级数组。
[mutableArray sortUsingSelector:@selector(caseInsensitiveCompare:)];
在这种情况下,包含在内的项目会按升序且不区分大小写的顺序排列(@"alpha"、@"beta" 和@"epsilon")。