iOS 6 处理托管对象后台保存的标准方法是什么(2013 年)?

标签 ios multithreading core-data restkit magicalrecord

去年我使用 RestKit 0.10 在后台无缝下载和保存核心数据对象。然而,当我在 2013 年尝试使用 restkit 时,我注意到他们已经取消了 ActiveRecord 模式,我依靠它来抽象出后台保存的所有不愉快。

我发现 MagicalRecord 框架中存在 ActiveRecord 模式,但我能找到的大部分文档都是针对 2.x 版本的,而我的 cocoapods 安装的是 3.x。

我花了最后 2 个小时进行搜索,找到了很多已经过时并且不再适用于这些新框架的答案。

这提出了一个问题:使用 2013 年可用的框架在后台保存核心数据对象的标准/最简单方法是什么?我应该尝试其他框架吗?

最佳答案

如果您不使用任何外部库,如 Magical Record 或 RestKit,而只是使用所有手动操作,则可以利用新的 NSManagedObjectContext API。

您现在可以让上下文嵌套在父子关系中,您还可以告诉每个上下文在它自己的线程中执行一个 block 。因此,我的建议是为您的应用程序采用以下结构:

1) 后台保存上下文。这将是唯一直接向数据库保存数据和从数据库读取数据的上下文。

2) 在主线程上初始化的上下文将成为您在应用程序中需要执行的所有操作的访问点,尤其是更新 UI。此上下文将是保存上下文的子项。

3) 根据需要,您将创建在后台线程上执行工作的后台上下文,例如从网络加载数据并在 NSManagedObject 实例中序列化这些数据。此上下文将是主上下文的子上下文。

4) 每次您在上下文中调用-[NSManagedObjectContext save:] 时,您也应该在它的parentContext 中调用相同的方法。为此,您可以在 NSManagedObjectContext 的类别中使用一个方便的方法,其内容如下所示:

- (void)saveSelfAndParent {
    [self save:NULL];
    [self.parentContext performBlock:^{
        [self.parentContext saveSelfAndParent];
    }];
}

这已经是线程安全的配置,您的更改会将更改传播到数据库。请注意,由于保存上下文没有父级(因此 self.parentContext 将为 nil),performBlock: 不会使应用程序崩溃。

这是一个示例,假设您使用 Grand Central Dispatch (GCD) 开始后台工作,则需要执行以下操作:

dispatch_async(dispatch_async_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
    NSManagedObjectContext *context = [[NSManagedObjectContext alloc] initWithConcurrencyType: NSPrivateQueueConcurrencyType];
    context.parentContext = mainContext;

    // do some expensive job
    ...

    // initialize a new NSManagedObject instance using the information we calculated
    NSManagedObject *myObject = ...;

    // once we're done, let's save the context
    [context saveSelfAndParent];
});

请注意,我们使用私有(private)队列并发类型(NSPrivateQueueConcurrencyType)初始化上下文,它告诉上下文他是后台上下文。这非常重要!

就是这样! :)

有关更多信息,请参阅 NSManagedObjectContext Class Reference .

关于iOS 6 处理托管对象后台保存的标准方法是什么(2013 年)?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17152696/

相关文章:

java - 运行线程对象的多个实例

java - 处理许多客户端的最佳方法(使用线程?)

c# - 如何将现有联系人添加到现有组

ios - Alamofire 4.4.0 : Extra Argument 'Method' in Call: Do not know What is Throwing Error

ios - Swift 4 按第一个值排序字典

ios - 在 Swift 中创建线程安全数组

swift - 基于对多引用对项目进行排序

swift - 通过 fetchedResultsController 在 Core Data 中使用大型基础

iphone - NSURL 到 NSData(Cocoa 错误 256。)

ios - AVCaptureDevice.requestAccess 使用 UINavigationController 呈现意外行为