核心数据:索引x处的获取对象具有乱序部分名称'xxxxxx.对象必须按节名称排序

six*_*way 21 iphone core-data objective-c nsfetchedresultscontroller ios

我知道我不是第一个提出这个问题的人,但我真的很难过......

基本上我有一个带两个按钮的屏幕.每个按钮根据日期将数据加载到下面的桌面视图中.在第一个tableview的第一次加载时(默认选中左键),一切正常.如果我点击右键,我得到一个空白的tableview,我得到错误

索引x处的获取对象具有无序部分名称'xxxxxx.对象必须按节名称排序.

切换回左表视图,数据消失了.两个tableviews都是空的.

每个tableview有2个部分,具体取决于项目的开始时间.如果我删除部分数据显示正常.不幸的是我需要它们..数据分为两部分,如下所示:

@interface NSString(agendaSessionKeyPath)
@property (nonatomic, readonly) NSString *sessionSection;
@end

@implementation NSString(agendaSessionKeyPath)

- (NSString *)sessionSection
{
    int timeValue = [[self stringByReplacingOccurrencesOfString:@":" withString:@""] intValue]; //turns 11:00 to 1100
    if (timeValue < 1200)
        return @"Morning";
     else
        return @"Afternoon";
}
Run Code Online (Sandbox Code Playgroud)

获取请求

- (void)viewDidLoad
{
     //other viewDidLoad stuff
    [self fetchSessions];
}
Run Code Online (Sandbox Code Playgroud)

根据日期从左右按钮对数据进行排序的方法:

- (void)fetchSessions
{
    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    [dateFormatter setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:0]];
    [dateFormatter setDateFormat:@"yyyy-MM-dd"];

    NSDate* date = nil;
    if (selected == 0) //left button is selected
    {
        date = [dateFormatter dateFromString:@"2012-09-26"];
    }
    else if (selected == 1) //right button is selected
    {
        date = [dateFormatter dateFromString:@"2012-09-27"];
    }

    NSPredicate *predicate = [NSPredicate predicateWithFormat:@"date == %@", date];
    [self.fetchedResultsController.fetchRequest setPredicate:predicate];

    NSError *error;
    if (![[self fetchedResultsController] performFetch:&error]) {
        NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
    }
}
Run Code Online (Sandbox Code Playgroud)

取结果控制器

- (NSFetchedResultsController *)fetchedResultsController {
    self.managedObjectContext = [[MATCDatabaseController sharedDatabaseController] managedObjectContext];
    if (_fetchedResultsController != nil) {
        return _fetchedResultsController;
    }

    NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] initWithEntityName:@"Session"];

    NSSortDescriptor *sort = [[NSSortDescriptor alloc]
                              initWithKey:@"title" ascending:YES];
    NSSortDescriptor *timeSort = [NSSortDescriptor sortDescriptorWithKey:@"timeValue" ascending:YES];
    [fetchRequest setSortDescriptors:@[timeSort, sort]];
    [fetchRequest setFetchBatchSize:20];

    NSFetchedResultsController *theFetchedResultsController =
    [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest
                                        managedObjectContext:self.managedObjectContext sectionNameKeyPath:@"startTime.sessionSection"
                                                   cacheName:nil];

    self.fetchedResultsController = theFetchedResultsController;
    [self.fetchedResultsController setDelegate:self];

    return _fetchedResultsController;

}
Run Code Online (Sandbox Code Playgroud)

任何帮助表示赞赏!

Jod*_*ins 25

好的,我确实快速偷看了.

您使用以下命令初始化FRC:

[[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest
                                    managedObjectContext:self.managedObjectContext
                                      sectionNameKeyPath:@"startTime.sessionSection"
                                               cacheName:nil];
Run Code Online (Sandbox Code Playgroud)

它告诉它你的章节标题是通过关键路径获得的startTime.sessionSection.

现在,给予FRC的获取请求的第一个排序描述符将用于对这些部分进行排序.您首先提供的排序描述符timeValue似乎不正确.

您的第一个排序描述符应指定节标题的排序.改变这一点,你可能会很高兴.

编辑

谢谢大家的信息.我虽然有点失落.你的意思是我应该在startTime.sessionSection上添加一个排序描述符,然后再将它分配给sectionNameKeyPath吗?我试过了,但还是没有运气.timeValue和startTime.sessionSection是相关的.可能是吗? - 很好

您必须确保第一个排序描述符将根据该部分正确排序数据.在你的情况下,时间被转换成单词.您的初始排序描述符有时间,并且当数据按时间排序时,这些部分未正确排序,这会导致您的错误.

第一个排序描述符必须满足节数据.所以,最初,我会尝试......

[fetchRequest setSortDescriptors:@[
    [NSSortDescriptor sortDescriptorWithKey:@"startTime.sessionSection"
                                  ascending:NO],
    [NSSortDescriptor sortDescriptorWithKey:@"timeValue"
                                  ascending:YES],
    [NSSortDescriptor sortDescriptorWithKey:@"title"
                                  ascending:YES] ];
Run Code Online (Sandbox Code Playgroud)

请注意,如果您有大量数据,您可能会发现您的部分机制变慢.如果发生这种情况,您可能希望将此部分数据添加到数据库中.

  • 对.我之前遇到过同样的问题,这就是解决方案.首先按照与段索引相同的键路径排序,然后按所需的行排序. (2认同)