简体   繁体   English

如何在不复制项目的情况下更新NSMutableDictionary中对象的值

[英]How to update values of objects in NSMutableDictionary without duplicating the item

Apologies if this question is very similar to one I asked previously . 如果这个问题与我之前问过的非常相似, 深表歉意。 However, I am having a new issue I did not encounter previously. 但是,我遇到了一个以前未遇到的新问题。

So, I have a bunch of UISwitch elements that are dynamically created based on values (labels and ID numbers) that are stored in a plist. 因此,我有一堆UISwitch元素是根据存储在plist中的值(标签和ID号)动态创建的。 I basically read the plist file and get an array of the items and for each one create the UISwitch. 我基本上阅读了plist文件并获得了一系列的项,并为每个项创建了UISwitch。 This part is all working great. 这部分工作很好。

The ultimate intent is for the user to be able to make selections with UISwitch and keep track of the value of those switch selections and then save them to Core Data. 最终目的是使用户能够使用UISwitch进行选择,并跟踪这些开关选择的值,然后将其保存到Core Data。

This is almost working perfectly, except whenever the user interacts with a switch, it adds a completely new object and key to the NSMutableDictionary 这几乎可以完美地工作,除非用户每次与开关交互时,它都会向NSMutableDictionary添加一个全新的对象和密钥。

Here is a block of my code I use to build the UI and update the NSMutableDictionary. 这是我用来构建UI和更新NSMutableDictionary的代码块。

.h 。H

@property int yPosStart;
@property NSString *switchValue;
@property (nonatomic, strong) UISwitch *qualifierSwitch;
@property (nonatomic, strong) NSMutableDictionary *evqValuesDict;

.m .m

for (int i =0; i < [evqArray count]; i++)
{
    id selector = [evqArray objectAtIndex:i];
        NSLog(@"selector: %@", selector);

    NSString *labelText = selector[@"label"];
        NSLog(@"labelText: %@", labelText);

    NSString *evqQualifierID = selector[@"event_qualifier_id"];
        NSLog(@"evqQualifierID: %@", evqQualifierID);

    NSInteger b = [evqQualifierID integerValue];

    // for every item in the array, add 35 pixels to the xPosStart
    _yPosStart = _yPosStart + 35;

    // Convert integer into CGFloat for positioning
    CGFloat yPosition = _yPosStart;

    UILabel *switchLabel = [[UILabel alloc] initWithFrame:CGRectMake(60, yPosition, 240, 27)];

    [switchLabel setText:labelText];

    _qualifierSwitch = [[UISwitch alloc] initWithFrame:CGRectMake(0, yPosition, 0, 0)];

    // add an incrementing tag so the siwtch interactions are unique
    _qualifierSwitch.tag = b;

    [myScroll addSubview:_qualifierSwitch];

    [myScroll addSubview:switchLabel];

    //Matcht the saved value to the switch
    _dbSwitchValue = [_evqSavedValues objectForKey:evqQualifierID];
        NSLog(@"myString2: %@", _dbSwitchValue);

    if ([_dbSwitchValue isEqualToString:@"Yes"]) {
        [_qualifierSwitch setOn:YES animated:YES];
    } else {
        [_qualifierSwitch setOn:NO animated:YES];
    }

    if (_qualifierSwitch.on)
    {
        _editSwitchValue = @"Yes";

    } else {
        _editSwitchValue = @"No";
    }

    [_qualifierSwitch addTarget:self action:@selector(evqChangeSwitch:) forControlEvents:UIControlEventTouchUpInside];

    [_evqValuesDict setObject:_editSwitchValue forKey:evqQualifierID];

}

- (void)evqChangeSwitch:(id)sender {
NSLog(@"evqSwitch: %@", _qualifierSwitch);
NSLog(@"_evqValuesDict at start of method: %@", _exqValuesDict);

//get the sender's tag value
NSInteger i = [sender tag];

//cast the tag value into a string for comparison to the string value for purposes of matching the dictionary key
NSString *tagID = [NSString stringWithFormat:@"%ld", (long)i];

NSLog (@"tagID:  %@:", tagID);

if([sender isOn]){

    NSLog(@"Switch is ON for tagID: %@", tagID);
    //Set string for display purposes elsewhere
    switchValue = @"Yes";
    [_exqValuesDict removeObjectForKey:tagID];
    [_evqValuesDict setObject:switchValue forKey:tagID];

} else {

    NSLog(@"Switch is OFF for tagID: %@", tagID);
    //Set string for display purposes elsewhere
    switchValue = @"No";
    [_exqValuesDict removeObjectForKey:tagID];
    [_evqValuesDict setObject:switchValue forKey:tagID];

}

NSLog(@"_evqValuesDict at end of method: %@", _evqValuesDict);

} }

Here are the logs at the beginning of the evqChangeSwitch method, and at the end. 这是evqChangeSwitch方法的开头和结尾的日志。

_evqValuesDict at start of method: {
3 = No;
1 = No;
2 = No;
}

evqValuesDict at end of method: {
3 = No;
2 = No;
2 = Yes;
1 = No;
}

So you can see that it appears that for each switch that has been selected, a duplicate is being created. 因此,您可以看到似乎为每个已选择的开关创建了一个副本。

Once the new, apparently duplicated value is in the NSMutableDictionary, the value for that key is actually properly updated. 一旦新的,显然重复的值位于NSMutableDictionary中,该键的值实际上就会正确更新。

I am building and testing against iOS9 and running XCode 7.1 我正在针对iOS9构建和测试并运行XCode 7.1

Solved it by simplifying everything. 通过简化一切来解决。 And I think it wasn't working because I was trying to use a new string (new memory pointer) to update objects for keys . 而且我认为它不起作用,因为我试图使用新的字符串(新的内存指针)来更新键的对象。 So my guess is (without having completely researched this) is that when NSMutableDictionary is doing setValue: for Key: it is referencing the memory address of the object, NOT the string value. 因此,我的猜测是(在尚未完全研究的情况下)当NSMutableDictionary正在执行setValue:for Key时:它是在引用对象的内存地址,而不是字符串值。

The main change I made was to use a single property evqQualifierID to keep track of the dictionary keys. 我所做的主要更改是使用单个属性evqQualifierID来跟踪字典键。

h. H。

@property (nonatomic, strong) NSString *evqQualifierID;

m.

- (void)evqChangeSwitch:(id)sender {
NSLog(@"evqSwitch: %@", _qualifierSwitch);
NSLog(@"_evqValuesDict at start of method: %@", _exqValuesDict);

//get the sender's tag value
NSInteger i = [sender tag];

//cast the tag value into a string for comparison to the string value for purposes of matching the dictionary key
NSString *tagIDString = [NSString stringWithFormat:@"%ld", (long)i];

NSLog (@"tagIDString:  %@:", tagIDString);

if([sender isOn]){

    NSLog(@"Switch is ON for tagIDString: %@", tagIDString);
    //Set string for display purposes elsewhere
    switchValue = @"Yes";

} else {

    NSLog(@"Switch is OFF for tagIDString: %@", tagIDString);
    //Set string for display purposes elsewhere
    switchValue = @"No";
}

[_evqValuesDict setObject:switchValue forKey:_evqQualifierID];

NSLog(@"_evqValuesDict at end of method: %@", _evqValuesDict);
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM