使用NSManagedObject子类来传输持久性和非持久性数据

时间:2013-04-11 16:41:41

标签: ios core-data nsmanagedobject nsmanagedobjectcontext

我对如何使用某些核心数据的NSManagedObject子类来处理持久数据和非持久数据有一些想法。

假设您有一个配方应用程序,显示您自己的CoreData配方列表,在同一个应用程序中,您也可以搜索其他用户配方。 这些其他用户配方当然来自API,我们不希望将它们保存到核心数据中。 但我们想要的是我们的配方细节View Controller,无论是给定持久配方还是非持久性配方,它都可以起作用。 我自然认为我们应该在数据周围使用相同的对象包装器,让我们的View Controller对数据的来源视而不见。

问题是NSManagedObject子类不能手动初始化,必须插入上下文中。这对我们的其他用户食谱不利。另一方面,对于我们自己的配方,我们需要将这些对象插入到上下文中。

我有几个解决方案,但我真的很想看看你们对这个问题的看法。

您是否认为这是一些实现问题,应该通过将两个数据对象包装到一个对象中来解决?例如,通过覆盖所有getter和setter来处理coredata对象和NSDictionary对象?

或者它是一个体系结构问题,您可以通过嵌套NSManagedContext或使用多个持久性存储(一个在内存中,另一个在Sqlite中)来解决它?

3 个答案:

答案 0 :(得分:7)

实际上,您可以创建NSManagedObject实例,而无需将它们插入上下文中。只需将nil作为托管对象上下文参数传递。做类似的事情:

NSEntityDescription *myRecipeEntity = [NSEntityDescription entityForName:@"MyRecipeEntity" inManagedObjectContext:[self managedObjectContext]];
MyRecipeClass *recipe = [[MyRecipeClass alloc] initWithEntity:myRecipeEntity insertIntoManagedObjectContext:nil]];

现在你有一个不在任何环境中的配方实例。

如果您以后想将其添加到上下文中:

[[self managedObjectContext] insertObject:recipe];

如果您不想插入它,请将其丢弃。

答案 1 :(得分:1)

我可能只是使用一个你永远不会保存的单独上下文,这似乎是最简单的路径。

答案 2 :(得分:0)

模型配置 - 内存存储和sqlite支持存储。

我会认真考虑使用模型配置和两种持久存储类型: 内存和sqlite支持。

但这也意味着您必须为可下载数据创建单独的实体,这样可以使您可以将某些配方保持持久性并且在它们都是配方时具有一些临时性。此外,您不能在不同持久性存储中的实体之间建立关系。您将放弃反向关系的好处,并且必须使用获取的属性来模仿它。

总而言之,这是一个可行的选择,有一些缺点。

隔离的托管对象上下文

使用单独的托管对象上下文的最大优点是,您可以对持久数据和临时数据使用相同的配方实体。您必须避免保存临时上下文,并且必须从持久性存储中引入所有更改,或者从具有您保存的数据的其他上下文中进行合并。

这种替代方案的挑战在于,您必须在这个孤立的上下文之上构建大部分UI以进行读取,但是您所做的所有永久性更改都需要保存到主上下文中,并通过合并到隔离的上下文中传播回来。这可能会引入一些棘手的情况,但我认为这是可行的。