我是iOS / Cocoa的新手,我对核心数据有一个非常基本的问题。我正在通过互联网查找合适的答案/解决方案,但我无法做到。
所以问题是如何处理核心数据的唯一性?我知道核心数据不是数据库,它就像对象图。让我们假设我们有一个名为'User'的实体,其属性'id'和'name'以及与其他实体的一些关系。现在我们要更新特定用户的名称(例如,Web服务为我们提供了id和新名称)。
这是我以前做过的方式:
NSFetchRequest *request = [[NSFetchRequest alloc] init];
[request setEntity:[NSEntityDescription entityForName:@"User" inManagedObjectContext:context]];
[request setPredicate:[NSPredicate predicateWithFormat:@"id == %@", anId]];
NSError *error = nil;
NSArray *results = [context executeFetchRequest:request error:&error];
User *user = [results lastObject];
但是我听说这是不好的做法。是因为带谓词的提取请求非常慢吗?我无法想象这是一件大事。据我所知,没有其他方法可以获得一个唯一的对象,而不是遍历每个对象并检查是否相等..
获取实体的所有对象,将它们放入数组并手动循环(而不是获取请求)会更有效吗?
NSFetchRequest *request = [[NSFetchRequest alloc] init];
[request setEntity:[NSEntityDescription entityForName:@"User" inManagedObjectContext:context]];
NSError *error = nil;
NSArray *results = [context executeFetchRequest:request error:&error];
User *resultUser;
for(User *user in results){
if([user.id isEqual:anId]) resultUser = user;
}
请帮我找到正确的道路和谢谢。
答案 0 :(得分:4)
如果你有一个你正在获取的属性的索引(模型编辑器中有一个复选框),那么使用等式谓词进行提取肯定会高效得多。实际上,获取所有对象并在内存中迭代它们永远不会更有效,但索引会使差异更显着。
答案 1 :(得分:1)
您不是获取唯一对象,而是包含名义上唯一的属性值的对象。
所有托管对象都是唯一的实例,但Core Data中没有任何内容强制执行属性值是唯一的。原则上,您可以拥有任意数量的唯一托管对象,这些对象都具有相同的属性值。只有关系在对象图中强制执行唯一的位置。
如果您的应用需要,则没有特别的理由不获取包含特定值的特定对象。
我认为您所阅读的内容是警告不要尝试将类似SQL的键值填充到实体中,然后尝试使用谓词将托管对象与这些键一起链接,例如执行以下操作:
EntityOne{
sqlKey:string
}
EntityTwo{
sqlKey:string
}
...然后尝试将两个实体的对象与谓词相关联。
(anEntityOneObject.)sqlKey == anEntityTwoObject.sqlKey
...而不仅仅是在数据模型中设置关系。
EntityOne{
two<-->EntityTwo.entityOne
}
EntityTwo{
one<-->EntityOne.two
}
...只需使用AnEntityOneObj.two
找到相关对象。