iPhone - получение уникальных значений из объекта NSArray - PullRequest
54 голосов
/ 17 сентября 2009

У меня есть NSArray, сформированный с объектами пользовательского класса. Класс имеет 3 строковых свойства (city, state, zip). Я хотел бы получить все уникальные значения состояния из array.

Я прочитал класс NSPredicate, но не смог понять, как его использовать в этом случае. Единственные примеры, которые я мог найти, были для строковых операций.

Может кто-нибудь помочь мне?

Ответы [ 2 ]

136 голосов
/ 17 сентября 2009

Посмотрите на keypaths . Они очень мощные, и я использую их вместо классов NSPredicate большую часть времени. Вот как бы вы использовали их в своем примере ...

NSArray *uniqueStates;
uniqueStates = [customObjects valueForKeyPath:@"@distinctUnionOfObjects.state"];

Обратите внимание на использование valueForKeyPath вместо valueForKey .

Вот более подробный / надуманный пример ...

NSDictionary *arnold = [NSDictionary dictionaryWithObjectsAndKeys:@"arnold", @"name", @"california", @"state", nil];
NSDictionary *jimmy = [NSDictionary dictionaryWithObjectsAndKeys:@"jimmy", @"name", @"new york", @"state", nil];
NSDictionary *henry = [NSDictionary dictionaryWithObjectsAndKeys:@"henry", @"name", @"michigan", @"state", nil];
NSDictionary *woz = [NSDictionary dictionaryWithObjectsAndKeys:@"woz", @"name", @"california", @"state", nil];

NSArray *people = [NSArray arrayWithObjects:arnold, jimmy, henry, woz, nil];

NSLog(@"Unique States:\n %@", [people valueForKeyPath:@"@distinctUnionOfObjects.state"]);

// OUTPUT
// Unique States:
// "california",
// "michigan",
// "new york"
122 голосов
/ 17 сентября 2009

Абсолютно простой вкладыш:

NSSet *uniqueStates = [NSSet setWithArray:[myArrayOfCustomObjects valueForKey:@"state"]];

Хитрость в том, что метод valueForKey: NSArray. Это будет выполнять итерацию по вашему массиву (myArrayOfCustomObjects), вызывать метод -state для каждого объекта и создавать массив результатов. Затем мы создаем NSSet с результирующим массивом состояний для удаления дубликатов.


Начиная с iOS 5 и OS X 10.7, есть новый класс, который также может это делать: NSOrderedSet. Преимущество упорядоченного набора состоит в том, что он удаляет все дубликаты, но также поддерживает относительный порядок.

NSArray *states = [myArrayOfCustomObjects valueForKey:@"state"];
NSOrderedSet *orderedSet = [NSOrderedSet orderedSetWithArray:states];
NSSet *uniqueStates = [orderedSet set];
...