从单个NSDictionaryObject创建的多个NSMutableDictionary对象显示相同的值

时间:2014-05-04 09:34:24

标签: objective-c cocoa-touch nsmutablearray nsmutabledictionary

我有 inputArray ,其值低于:

@[@“one”,@“two”,@“three”,@“four,@“five”];

我有一个带有以下键值的plist文件:

<dict>
    <key>displayProperties</key>
    <dict>
        <key>leftPadding</key>
        <integer>0</integer>
    </dict>
    <key>displayValues</key>
    <dict>
        <key>percentageValueKey</key>
        <string>percentageValueKey</string>
        <key>subtitleText</key>
        <string></string>
        <key>actualValueKey</key>
        <string></string>
        <key>titleValue</key>
        <string>Title Value</string>
    </dict>
</dict>

从上面的plist我创建一个字典: mappingDict

现在我正尝试执行以下步骤:

1.  Initialize an empty mutable array- finalArray.
2.  Iterate through each object in inputArray.
3.  Create mutableDictionary from mappingDict.
4.  Replace value of a key in mutableDictionary with currently iterated value in inputArray.
5.  Add the updated mutableDictionary to finalArray.

我使用下面的代码:

- (void)generateFinalPlist
{
    // populate final array
    NSMutableArray *finalArray = [[NSMutableArray alloc] initWithCapacity:2];

    [self.inputArray enumerateObjectsUsingBlock:^(NSString* inputRecord, NSUInteger idx, BOOL *stop) {
        NSMutableDictionary *mutableDict = [[NSMutableDictionary alloc] initWithDictionary:self.mappingDict];
        mutableDict[@"displayValues"][@"percentageValueKey"] = inputRecord;
        [finalArray addObject:mutableDict];
    }];

    // generating plist file
    [finalArray writeToFile:self.finalPlistPath atomically:YES];
}

问题是:

finalArray中的每个对象都显示'five'作为'percentageValueKey'的对象。

如果我做错了,请提出建议吗?

解决:

请检查Martin R添加的答案和评论。

1 个答案:

答案 0 :(得分:3)

NSMutableDictionary *mutableDict = [[NSMutableDictionary alloc] initWithDictionary:self.mappingDict];

创建一个包含self.mappingDict的键和值的新词典 不会复制值,这意味着

mutableDict[@"displayValues"]

仍然引用self.mappingDict中的值,您正在修改它 循环的每一步中的字典。尝试

NSMutableDictionary *mutableDict = [[NSMutableDictionary alloc] initWithDictionary:self.mappingDict
                                        copyItems:YES];

代替。

更新 这也不起作用,因为copyItems:YES会导致子目录 复制,这使它们不可变。你需要的是一个“深度可变副本” 所有子目录也都是可变的。

但是有一个更简单的解决方案。而不是复制self.mappingDict,只需重新阅读它 从plist作为一个可变字典:

NSMutableDictionary *mutableDict = [NSMutableDictionary dictionaryWithContentsOfFile:mappingPlistPath];

这为循环中的每个枚举步骤提供了独立的可变字典。