2010-02-25 2 views
3

Я немного смущен кодировкой ключевых значений и многими отношениями. Я прочитал, что, имея такие отношения, я должен использовать [object mutableArrayValueForKey: @ "key"]; для извлечения изменчивого массива, который содержит объекты в этом упорядоченном соотношении.отношения с ключом и ко многим отношениям

Что я не понимаю, в чем разница между mutableArrayValueForKey или просто valueForKey.

Позвольте мне проиллюстрировать на примере (массив является NSMutableArray из установки в качестве самостоятельной собственности):

id array1= [self valueForKey:@"array"]; 

NSLog(@"first element %@",[array1 objectAtIndex:1]); 

id array2 = [self mutableArrayValueForKey:@"array"]; 

NSLog(@"first element %@",[array2 objectAtIndex:1]); 

Оба вызовы возвращают точно так же. В этом случае, какая польза или какая-то другая из второй?

Cheers!

ответ

6

mutableArrayValueForKey не возвращает «массив», он возвращает прокси-сервер для «массива». Вы можете увидеть это, если вы печатаете из классов:

NSLog(@"%@", [self.array class]); 
NSLog(@"%@", [[self valueForKey:@"array"] class]); 
NSLog(@"%@", [[self mutableArrayValueForKey:@"array"] class]); 

Печатается:

2010-02-24 20:06:44.258 Untitled[25523:a0f] NSCFArray 
2010-02-24 20:06:44.275 Untitled[25523:a0f] NSCFArray 
2010-02-24 20:06:44.276 Untitled[25523:a0f] NSKeyValueSlowMutableArray 

Чтение по documentation для mutableArrayValueForKey для получения подробной информации о том, как работает, что прокси-сервер. В этом конкретном случае у вас есть настоящий NSMutableArray как ivar. Но что, если бы такого ивара не было? Вы можете реализовать KVC без поддержки ivar, используя методы, такие как countOf<Key> и objectIn<Key>AtIndex:. Нет никакого правила, что существует реальный «массив» ivar, если вы можете вернуть разумные результаты методам KVC.

Но что, если вы хотите открыть интерфейс NSMutableArray, но у вас нет реального NSMutableArray? Вот что такое mutableArrayValueForKey для. Он возвращает прокси-сервер, который при доступе будет переводиться в методы KVC обратно к вам, включая отправку вам мутирующих многих методов, таких как insertObject:in<Key>AtIndex:.

Это происходит даже в случае, если у вас есть настоящий ivar (как в вашем случае), вы просто не заметите его, потому что прокси ведет себя так, как настоящий объект.

+0

Yay для подробного объяснения! – dreamlax

+0

благодарит за ответ! – theprole

0

Первый элемент на самом деле objectAtIndex:0, а не objectAtIndex:1.

Кроме того, второй метод гарантирует, что вы можете изменить возвращенный массив с помощью addObject: и removeObjectAtIndex:, даже если значение для ключа @"array" является неизменяемым массивом.

+0

yes Я знаю, что первый элемент равен 0. Код не означает, что он был первым. Второй момент имеет смысл, но является ли это единственным преимуществом? что он возвращает изменяемый массив? Почему (если исходный объект является NSMutableArray) не valueForKey возвращает изменчивый? – theprole

+0

Кроме того, если вы пишете массив (NSMutableArray *); метод таким образом, что он возвращает NSMutableArray, тогда первый вызов фактически получит изменчивый массив, поэтому он сможет использовать addObject: – theprole

+3

В коде говорится: «NSLog (@« первый элемент% @ », ...) 'и затем регистрирует элемент * second *. – dreamlax