NSFetchedResultsController在后台线程上执行

时间:2011-08-01 12:31:08

标签: core-data grand-central-dispatch

我必须在后台线程上通过NSFetchedResultsController执行提取。

我目前的解决方案结构如下:

dispatch_queue_t fetchQueue = dispatch_queue_create("backgroundfetching", NULL);

dispatch_async(fetchQueue,^{
    // 1. Create NSManagedObjectContext
    // 2. Create NSFetchRequest
    // 3. Create NSFetchedResultsController
    // 4. PerformFetch

    dispatch_async(dispatch_get_main_queue(),^{
        [[self table] reloadData];
    });
});

dispatch_release(fetchQueue);

我的第一次测试运行得很好,但这是适当的方式吗?

2 个答案:

答案 0 :(得分:5)

由于获取的结果控制器旨在控制定义表视图的数据,因此它属于运行UI的前台线程/操作。把它放在后台线程上是没有意义的,因为你将失去首先使用它的所有优点。

我还会担心跨异步线程发送FRC委托消息的影响。我不确定会有多可靠。

说了这么多,你的实现草图看起来很好。

答案 1 :(得分:1)

我相信这种方法存在根本性的错误,因为您在线程之间共享托管对象(您在一个线程上获取对象并在主线程上引用它们)。在实践中它会起作用,但有时会导致崩溃。因为Apple明确表示跨线程共享托管对象的唯一方法是使用objectWithID:方法或MOCDidSave通知。

来自Core Data Programming Guide

  

您在后台线程上获取一个托管对象上下文,并且   将获取的对象的对象ID传递给另一个线程。在里面   第二个线程(通常是应用程序的主线程,所以你   然后可以显示结果),你使用第二个上下文来进行故障   具有这些对象ID的对象(使用objectWithID:实例化   对象)。