2010-01-24 56 views
2

我正在使用NSFetchedResultsController以及一个UITableViewController。为什么NSFetchedResultsController不能正确加载节标题?

我在我的核心数据模型中创建了一个瞬态字段,用作我的UITableView部分的标签。该字段的名称是“sectionIndex”。在我的应用程序中,“客户”实体具有许多“作业”(1到多个) - 因此,我的检索作业的查询通过其关联的“客户”名称对它们(通过部分)进行分组。

我在我的代码库中实现了这个方法,作为'Job'实体上的一个类别。

@implementation Job (TransientMethods) 

- (NSString*)sectionIndex { 
    NSLog(@"JobWrapper.Job.sectionIndex: %@", self.client.name); 
    return self.client.name; 
} 

@end 

和字符串“sectionIndex”作为sectionNameKeyPath参数传递给NSFetchedResultsController的init方法。

如果我从模拟器中删除应用程序 - 那么应用程序第一次运行时,作业的首页会按照此处列出的sectionIndex方法,通过作业的Client.name正确检索并分组作业。在日志中,我可以从字面上看到多次调用此sectionIndex方法。

但是,应用程序的后续运行不会调用sectionIndex方法...然而,节标签仍然显示上一次运行的值。这是怎么发生的?运行之间是否存在一些魔术缓存?

这种行为会导致更大的问题。在查看UITableView时,如果我释放并分配具有稍微不同谓词的NSFetchedResultsController,并且结果集是相同大小,则这些相同的原始节名称将显示所有NEW结果!

当然,没有新的日志条目。这意味着列永远不会被查找,这意味着代码永远不会调用或查找瞬态字段。就好像这些领域不是错误的。

现在,如果备用查询返回不同数量的结果,则会装载部分名称。 IE:在这种情况下,日志显示 - 在每个按钮按钮上 - 调用'sectionIndex'方法以及在UITableView中显示的相应标签。

这太疯狂了 - 如果我有2个“活动”作业和2个“非活动”作业,并且我正在使用条形按钮在相应查询之间来回切换......则无论哪个部分标签都与初始查询相关联显示所有后续的表格视图。

当结果集中有不同的结果时,似乎sectionNameKeyPath字段仅由FetchedResultsController调用?实际结果不同 - 作业名称在实际行中正确显示 - 但同样,我不认为章节标签是错误的,或者正确地要求NSFetchedResultsController中的章节标签。我使用了以下内容:

- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section { 
    int count = [[results_ sections] count]; 
    if (count > section) { 
     id <NSFetchedResultsSectionInfo> sectionInfo = [[results_ sections] objectAtIndex:section]; 
     return [sectionInfo name]; 
    } 
    return nil; 
} 

其中results_是,我重新构建每个查询的NSFetchedResultsController。

我错过了什么吗?有没有办法手动清除核心数据缓存,以便它不再那么聪明,并且在每个查询中肯定会查找sectionNameKeyPath?

对于它的价值,我取消了xcdatamodel中字段的“Transient”选项,但我得到了相同的结果。从这个

最后一个anomally是,当我创建第一个工作作为活动的(不是默认启动视图) - 如果我也然后创建一个活动的工作...无源部分标签粘到两个。此外,当我关闭应用程序,并重新开始......无源部分标签仍然显示---尽管,标题画面上,我显示活动作业应呈现完全不同的标签。

我不能不认为这是一个核心数据的问题。重新启动应用程序正在返回数据以免出现重击是没有意义的。

+0

顺便说一句,这个代码(在完全相同的时间执行)显示该行的正确的价值观:工作*工作=( Job *)[results_ objectAtIndexPath:indexPath]; cell.textLabel.text = job.name;即:我知道查询正在运行,新的结果在“results_”对象中可用。 (stackoverflow的评论编辑器从所包含的代码片段中删除了所需的星号)。 – 2010-01-24 22:50:21

+1

请出示您的NSFetchedResultsController初始化代码。有一个缓存选项,我怀疑你有缓存设置。 – 2010-01-25 00:17:59

+0

确实,这工作。我用:results_ = [[NSFetchedResultsController的alloc] initWithFetchRequest:fetchRequest managedObjectContext:context_ sectionNameKeyPath:@ “sectionIndex” cacheName:@ “JobsControllerCache”];而如果我将缓存设置为零 - 它会起作用。谢谢。 – 2010-01-25 00:24:28

回答

4

Marcus S. Zarra's评论,我设置了cacheName为零:

results_ = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest 
      managedObjectContext:context_ 
      sectionNameKeyPath:@"sectionIndex" 
      cacheName:nil]; 
相关问题