【发布时间】:2011-06-24 11:05:18
【问题描述】:
为了在我的 iOS 项目中更新 Core Data 模型,我在服务器上查询 JSON 对象,这些对象在某种程度上与我的模型的托管实体相对应。我努力的最终结果是来自 JSON 输出的可靠更新解决方案。
对于本题中的示例,我将核心数据托管对象命名为existingObj,并将传入的 JSON 反序列化字典命名为 updateDict。棘手的部分是处理这些事实:
- 并非
existingObj的所有属性都存在于updateDict中 - 并非
updateDict的所有属性都在extistingObj中可用。 - 并非所有类型的
existingObj的属性都与 JSON 反序列化属性匹配。 (某些字符串可能需要自定义的 Objective-C 包装器)。 -
updateDict可能包含existingObj中未初始化 (nil) 的键的值。
这意味着在迭代更新的字典时,必须来回对属性进行一些测试。首先我要测试updateDict的属性是否存在于existingObj中,然后我使用KVC设置值,如下所示:
// key is an NSString, e.g. @"displayName"
if ([existingObj respondsToSelector:NSSelectorFromString(key)) {
[existingObj setValue:[updateDict objectForKey:key] forKey:key];
}
虽然这部分有效,但我不喜欢我实际上正在测试 displayName 作为吸气剂,而我即将调用 setDisplayName: 设置器(间接通过 KVC)。我更喜欢 [existingObj hasWritablePropertyWithName:key] 之类的东西,但我找不到这样做的东西。
这就引出了子问题 A:如果您只有属性的名称,如何测试属性设置器?
下一部分是我想根据它们的类型自动识别属性的地方。如果updateDict 和existingObj 的键@"displayName" 都有一个NSString,那么设置新值很容易。但是,如果updateDict 包含键 @"color" 的 NSString,即 @"niceShadeOfGreen",我想将其转换为正确的 UIColor 实例。但是如何测试existingObj 中接收属性的类型,以便知道何时转换值以及何时简单地分配?我希望有类似 typeOfSelector:
if ([existingObj typeOfSelector:sel] == [[updateDict objectForKey:key] class]) {
// regular assignment
} else {
// perform custom assignment
}
当然这是假代码。我不能依赖测试existingObj-property 值的类型,因为它可能是未初始化的或nil。
子问题 B:如果您只有属性的名称,如何测试属性的类型?
我想就是这样。我想这一定是这里已经存在的东西的欺骗,但我找不到它。也许你们可以?
干杯,EP。
附:如果您有更好的方法将自定义的 Objective-C 对象同步到反序列化的 JSON 对象,请分享!最后,结果才是最重要的。
【问题讨论】:
-
我建议您只需查询
updateDict的键你知道 并忽略所有其余的。 -
从上面的例子来看,这确实是一个可行的选择。然而,在现实世界的场景中,这会使托管对象的修改和更新变得非常复杂。这些对象由 30 多个键/属性组成,其中大部分是 NSString 或 NSNumber。如果上面的问题有解决方案,那么在双方都添加或修改原始类型时,同步不需要修改。
标签: properties css-selectors exists key-value-coding objective-c-2.0