Question

I have an inputArray with below values:

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

I have a plist file with below key values:

<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>

From above plist I am creating a dictionary: mappingDict.

Now I am trying to perform below steps:

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.

I have used below code for the same:

- (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];
}

Problem is:

Each of the object in finalArray is showing ‘five’ as object for ‘percentageValueKey’.

Please suggest, if I am doing anything wrong?

Solved:

Please check answer and comment added by Martin R.

Was it helpful?

Solution

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

creates a new dictionary containing the keys and values of self.mappingDict, but it does not copy the values, which means that

mutableDict[@"displayValues"]

still refers to the the value in self.mappingDict and you are modifying the same dictionary in each step of the loop. Try

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

instead.

Update: This does also not work because copyItems:YES causes the subdirectories to be copied, which makes them immutable. What you need is a "deep mutable copy" where all subdirectories are also mutable.

But there is an easier solution. Instead of copying self.mappingDict, just re-read it from the plist as a mutable dictionary:

NSMutableDictionary *mutableDict = [NSMutableDictionary dictionaryWithContentsOfFile:mappingPlistPath];

This gives you independent mutable dictionaries for each enumeration step in the loop.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top