繁体   English   中英

没有在dispatch_async中调用UITableView endUpdates

[英]UITableView endUpdates not being called in dispatch_async

我有几个表视图,这些表视图将JSON请求发送到服务器,将结果存储在核心数据中,并使用NSFetchedResultsController显示它们。 我正在尝试GCD,如下所示:

dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^{
    // Perform JSON requests.
    dispatch_async(dispatch_get_main_queue(), ^{
        [theTableView reloadData];
    });
});

但是,这会导致UI中发生一些奇怪的事情。 新的托管对象将呈现空白单元格,删除的托管对象将导致单元格重叠等。

但是,我发现如果执行此操作,所有内容将正确呈现。

- (void)controllerDidChangeContent:(NSFetchedResultsController *)controller
{
    dispatch_async(dispatch_get_main_queue(), ^{
        [theTableView endUpdates];
    });
}

我想知道的是,为什么这是必要的? 由于它是[theTableView reloadData]的结果而触发,为什么它不自动包含在主队列中? 我以为可能是因为我没有明确称呼它。 在那种情况下,我是否必须同样包装所有功能?

假设您从单独的线程中使用主NSManagedObjectContext ,这是不允许的。 对于后台导入,您必须创建一个单独的托管对象上下文,在该上下文中导入对象,然后将更改保存/合并到主上下文。

一种可能性是使用主管理对象上下文的上下文:

NSManagedObjectContext *childContext = [[NSManagedObjectContext alloc]
                         initWithConcurrencyType:NSPrivateQueueConcurrencyType];
childContext.parentContext = mainManagedObjectContext;
[childContext performBlock:^{
    // Perform JSON requests.
    // Save objects to childContext.

    NSError *error;
    BOOL success = [childContext save:&error];
}];

“私有并发类型”的上下文创建其自己的队列/线程,以便performBlock在后台执行(并且您需要/不必自己创建队列)。

保存childContext更改合并到父mainManagedObjectContext 这足以使获取的结果控制器获得有关更改的通知,并更新表视图。

有关受管对象上下文并发和嵌套上下文的更多信息,请参见《 OS X v10.7和iOS 5.0的核心数据发行说明》

原为

 [theTableView beginUpdates]

写在代码的任何地方? 尝试将其删除。 我怀疑UI怪异的事情正在发生,因为beginUpdates本身已经是异步的(不阻塞主线程),以便进行时髦的UITableView动画。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM