Различные ключи указывают на один и тот же объект (ы) в NSMutableDictionary - PullRequest
1 голос
/ 12 января 2011

У меня есть пользовательский объект с именем Person, который помимо прочего содержит поле NSString с именем descriptor, в котором хранится информация о том, каким человеком является объект Person (злой, грустный, дикий, счастливый, угрюмый, так далее). Все мои объекты Person находятся в NSMutableArray, но я бы хотел сохранить их в NSMutableDictionary таким образом:

Ключ: A, Объект: An NSMutableArray, где все Person объекты имеют descriptor, начинающиеся с 'A'

Ключ: B, Объект: An NSMutableArray, где все Person объекты имеют descriptor, начинающиеся с 'B'

Ключ: C, Объект: NSMutableArray, где все Person объекты имеют descriptor, начиная с 'C' и т.д ...

Я пытался сделать это в своем коде ниже, и в комментарии // POINT 1 ключи и массивы, кажется, совпадают, но в // POINT 2, когда я распечатываю полный словарь, все ключи имеют одинаковые значения!

Итак, я хотел знать, почему NSMutableArray, который у меня, кажется, не сохраняется, как я хочу в NSMutableDictionary?

- (void)buildDictionaryForIndexList {
    NSMutableDictionary *tempDict = [[[NSMutableDictionary alloc] init] autorelease];
    NSMutableArray *personsStartingWithLetter = [[NSMutableArray alloc] init];
    NSMutableArray *indexList = [[[NSMutableArray alloc] init] autorelease];
    NSInteger loopCounter = 1;
    NSString *firstLetter = [[[NSString alloc] init] autorelease];
    for (Person *v in persons) {
        firstLetter = [[v descriptor] substringWithRange:NSMakeRange(0, 1)];
        if ([indexList containsObject:firstLetter]) {
            [personsStartingWithLetter addObject:v];
            if (loopCounter == [persons count]) {
                [tempDict setObject:personsStartingWithLetter forKey:firstLetter];
            }
        } else {
            if (loopCounter > 1) {
                //POINT 1
                NSLog(@"%@",[indexList objectAtIndex:[indexList count]-1]);
                for (Person *q in personsStartingWithLetter) {
                    NSLog(@"%@",[q descriptor]);
                }
                [tempDict setObject:personsStartingWithLetter forKey:[indexList objectAtIndex:([indexList count] - 1)]];
                [personsStartingWithLetter removeAllObjects];
            }
            [indexList addObject:firstLetter];
            [personsStartingWithLetter addObject:v];
        } // else
        loopCounter++;
    } // for
     //POINT 2
    NSEnumerator *enumerator = [tempDict keyEnumerator];
    for (NSString *str in enumerator) {
        NSLog(@"%@",str);
        for (Person *c in [tempDict objectForKey:str]) {
            NSLog(@"%@",[c descriptor]);
        }
    }
    self.dictionary = tempDict;
} // buildDictionaryForIndexList

Так, например, в POINT 1 мой вывод:

A

Angry

Amiable

B

Воинственный

C

Cool

...

W

Дикий * * тысяча пятьдесят-одна

но в ТОЧКЕ 2 мой вывод

T

Wild

* +1058 * J

Wild

A

Wild

...

W

Wild

Ответы [ 2 ]

2 голосов
/ 12 января 2011

Измените [tempDict setObject:personsStartingWithLetter forKey:[indexList objectAtIndex:([indexList count] - 1)]]; (сразу после пункта 1) на [tempDict setObject:[[personsStartingWithLetter copy] autorelease] forKey:[indexList objectAtIndex:([indexList count] - 1)]];. Проблема в том, что NSDictionary копирует ключ, но сохраняет значение. Поэтому, если вы добавите непостоянный массив в словарь, а затем измените его, массив в словаре также изменится. Вам необходимо создать неизменяемую копию массива для помещения в словарь.

0 голосов
/ 13 февраля 2014

Весь метод немного усложнен.

- (void)buildDictionaryForIndexList 
{
    NSMutableDictionary *tempDict = [[[NSMutableDictionary alloc] init] autorelease];
    for (Person *v in persons)
    {
        NSString* firstLetter = [[v descriptor] substringWithRange:NSMakeRange(0, 1)];
        NSMutableArray* personsStartingWithLetter = tempDict [firstLetter];
        if (personsStartingWithLetter == nil)
        {
            personsStartingWithLetter = [NSMutableArray array];
            tempDict [firstLetter] = personsStartingWithLetter;
        }
        [personsStartingWithLetter addObject:v];
    } // for
    self.dictionary = tempDict;
}

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

...