NSPersistentContainer newBackgroundContext 的最佳实践是啥?

Posted

技术标签:

【中文标题】NSPersistentContainer newBackgroundContext 的最佳实践是啥?【英文标题】:What's the best practice for NSPersistentContainer newBackgroundContext?NSPersistentContainer newBackgroundContext 的最佳实践是什么? 【发布时间】:2018-06-24 21:22:00 【问题描述】:

我正在熟悉NSPersistentContainer。我想知道每次我需要在后台插入/获取一些实体或创建一个私有上下文时使用newBackgroundContext 生成一个私有上下文的实例是否更好,保留它并在应用程序的整个生命周期内用于所有后台任务.

文档还提供了方便的方法performBackgroundTask。只是想找出这里的最佳做法。

【问题讨论】:

【参考方案1】:

我通常推荐两种方法中的一种。 (还有其他可用的设置,但这是我使用过、测试过并推荐的两种设置。)

简单的方法

您从 viewContext 读取并写入 viewContext 并且只使用主线程。这是最简单的方法,并且避免了许多核心数据常见的多线程问题。问题是磁盘访问是在主线程上发生的,如果你做很多事情,它可能会减慢你的应用程序。

这种方法适用于小型轻量级应用。任何拥有少于几千个实体并且一次没有批量更改的应用程序都将是一个很好的候选者。一个简单的待办事项列表就是一个很好的例子。

复杂的方式

复杂的方法是仅从主线程上的 viewContext 读取,并在串行队列中使用 performBackgroundTask 完成所有写入。 performBackgroundTask 中的每个块都重新获取它需要的任何 managedObjects(使用 objectIds),并且它创建的所有 managedObjects 在块的末尾被丢弃。每个 performBackgroundTask 都是事务性的,并且 saveContext 在块的末尾被调用。更完整的描述可以在这里找到:NSPersistentContainer concurrency for saving to core data

这是一个强大且功能强大的核心数据设置,可以管理任何合理规模的数据。

问题是您总是要确保 managedObjects 来自您期望的上下文并且在正确的线程上被访问。您还需要一个串行队列来确保您不会遇到写冲突。而且您经常需要使用 fetchedResultsController 来确保在您持有指向实体的指针时不会删除它们。

【讨论】:

嗨@Jon Rose,你能指点我上面提到的以复杂方式做事的演示吗? 当然!这个问题的答案你可以找到更完整的解释:***.com/questions/42733574/…

以上是关于NSPersistentContainer newBackgroundContext 的最佳实践是啥?的主要内容,如果未能解决你的问题,请参考以下文章

如何处理 NSPersistentContainer.loadPersistentStores 中的错误?

NSPersistentContainer, performBackgroundTask, 调用 perform 啥都不做

NSPersistentContainer的loadPersistentStores的completionHandler是不是同步运行?

如何在 AppDelegate 中包含 NSPersistentContainer

NSPersistentContainer,performBackgroundTask,调用perform什么都不做

NSPersistentContainer newBackgroundContext 的最佳实践是啥?