NSFetchedResultsController让我发疯

时间:2010-03-14 16:40:08

标签: iphone nsfetchedresultscontroller

我使用NSFetchedResultsController从1个月开始构建应用程序,我正在测试3.1.2 SDK上的应用程序。问题是,我一直在我的应用程序中使用NSFetchedResultsController并正在使用SDK的3.1.2版本,现在我的客户说我应该使它与3.0版本兼容,截止日期几乎就在那里。

但每次我更改控制器处理的对象时都会崩溃,应用程序崩溃时会出现非常奇怪的错误。

删除某个部分中的最后一个对象时以及当一个更改使一个对象爱上另一个部分时出现问题。

我一直在使用Dave Mark和Jeff LaMarche的“更多iPhone 3开发解决iPhone SDK 3”中的示例代码。我还从link text

中添加了一些更改

以下是应用程序崩溃时控制台的示例输出。

***由于未捕获的异常'NSInternalInconsistencyException'而终止应用程序,原因:'无效更新:无效的节数。更新后的表视图中包含的节数(1)必须等于更新前的表视图中包含的节数(2),加上或减去插入或删除的节数(插入2个,0删除)。” 2010-03-14 16:23:29.758 Instaproofs [5879:207] Stack :(     807902715,     7364425,     807986683,     811271572,     815059090,     815007323,     211023,     4363331,     810589786,     807635429,     810579728,     3620573,     3620227,     3614682,     3609719,     27337,     810595174,     807686849,     807683624,     839142449,     839142646,     814752238 )

如果我知道NSFetchedResultsController是如此错误,我将永远不会使用它。

所以基本上我需要我的NSFetchedResultsControllerDelegate才能在3.0及以上的SDK上正常工作。

如果有人帮助我弄清楚我做错了什么,那将会节省生命。

2 个答案:

答案 0 :(得分:5)

从错误消息中可以看出,当您删除它们时,您正在将节插入表中。你的tableView dataSource只在更新后提供一个部分,即使你告诉tableView总共需要四个部分。

我认为这不是NSFetchedResultsController的错误,而是在简单的用例之外实现它很棘手。您的崩溃几乎肯定是由于您的控制器而发生的:didChangeObject:atIndexPath:forChangeType:newIndexPath委托方法。成功实现此方法的关键(至少在我的经验中)是要记住,changeTypes既是对象又是索引路径驱动的。这使得“更新”和“移动”在概念上变得棘手。

考虑更改托管对象的情况,以便在新的sectionNameKeyPath下进行排序。从概念上讲,我们认为对象已经“移动”到一个新的部分,因为fetchedResultsController现在在tableView的新标题下对其进行排序。但是,如果对象的indexPath没有改变,则fetchedResultsController认为这是“更新”而不是“移动”。

更糟糕的是,即使更改的托管对象仍保留相同的indexPath,fetchedResultsController中的其他对象现在可能具有新的indexPath,因为它们被更改所碰撞。这意味着您必须在委托方法的“更新”部分手动处理部分插入和部分删除。类似的问题需要在委托方法的“移动”部分解决。

LaMarche的解决方案试图以通用的方式解决这个问题,尽可能多地使用案例。通过尝试了解与您的用例相关的问题,您可以显着降低LaMarche使用的代码的复杂性。专注于代理方法的“更新”和“移动”部分,因为这些是您问题的最可能的罪魁祸首。

答案 1 :(得分:0)