在表格视图部分中对核心数据对象进行排序
Posted
技术标签:
【中文标题】在表格视图部分中对核心数据对象进行排序【英文标题】:Ordering core data objects inside a table view section 【发布时间】:2014-01-28 18:57:01 【问题描述】:我正在使用 NSSortDescriptors 对核心数据对象进行排序并根据日期属性创建表格视图部分。使用这种 SortDescriptor,表格视图部分按预期排序,但部分内的行也按相同的日期属性排序。有没有办法在每个部分内有另一个订购系统?我猜主要问题是核心数据存储日期对象的日期+时间值,这样就没有对象具有完全相同的日期值。但我需要根据另一个属性对同一部分内的对象进行排序。 谢谢。
这是我的 NSFetchedResultsController 代码:
-(NSFetchedResultsController*)fetchedResultsController
if (_fetchedResultsController != nil)
return _fetchedResultsController;
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc]init];
NSManagedObjectContext *context = self.managedObjectContext;
NSEntityDescription *entity = [NSEntityDescription entityForName:@"MyEntity" inManagedObjectContext:context];
[fetchRequest setEntity:entity];
NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc]initWithKey:@"itemDate" ascending:YES];
NSSortDescriptor *sortDescriptor1 = [[NSSortDescriptor alloc]initWithKey:@"itemName" ascending:NO];
NSArray *sortDescriptors = [[NSArray alloc]initWithObjects:sortDescriptor,sortDescriptor1, nil];
fetchRequest.sortDescriptors = sortDescriptors;
_fetchedResultsController = [[NSFetchedResultsController alloc]initWithFetchRequest:fetchRequest managedObjectContext:context sectionNameKeyPath:@"sectionIdentifier" cacheName:nil];
_fetchedResultsController.delegate = self;
return _fetchedResultsController;
编辑问题
这是添加到 cellForRowAtIndexPath 方法中的一段代码:
int indexpathsection = indexPath.section;
[self sortedSectionForIndex:indexpathsection];
NSLog(@"INDEXPATH= %ld", (long)indexPath.section);
这是马库斯提出的方法:
- (NSArray*)sortedSectionForIndex:(NSInteger)index
NSSortDescriptor *sort = [NSSortDescriptor sortDescriptorWithKey:@"priority" ascending:YES];
id section = [[self fetchedResultsController] sections][index];
NSLog(@"INDEX********* = %ld", (long)index);
NSArray *objects = [section objects];
NSArray *sorted = [objects sortedArrayUsingDescriptors:@[sort]];
return sorted;
【问题讨论】:
欢迎来到***!如果你展示你的数据结构/代码,你会得到更好的答案。 谢谢,我会将我的 NSFetchedResultsController 代码添加到我的问题中。 @CorleyBrigman,我已将代码添加到问题中。 【参考方案1】:NSFetchedResultsController
用于通过单个排序或一组排序来控制排序顺序。它不是为了做你想做的事。
但你可以做到,只是不够干净。
首先,讨论对一个部分进行排序。这不需要您编写自己的排序算法:
- (NSArray*)sortedSectionForIndex:(NSInteger)index
NSSortDescriptor *sort = [NSSortDescriptor sortDescriptorWithKey:@"MyKey" ascending:YES];
id section = [[self fetchedResultsController] sections][index];
NSArray *objects = [section objects];
NSArray *sorted = [objects sortedArrayUsingDescriptors:@[sort]];
return sorted
使用该方法,您可以在想要检索对象时要求对部分进行排序。但是,这是低效的,因为每次您想要触摸 UITableViewController
中的 LOT 的对象时都会进行排序。
取而代之的是,将这个示例与您的 NSFetchedResultsController
及其委托方法集成,以便您存储排序后的数组并保持它们同步。这样,您只需在数据更改时进行排序,而不是在每次方法调用时进行排序。
更新
我提供给您的排序代码不会对NSFetchedResultsController
内部 的内容进行排序。它获取该部分中的内容,对其进行排序并返回排序后的数组。所以你需要使用它返回的内容:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
NSArray *sorted = [self sortedSectionForIndex:[indexPath section]];
id object = [sorted objectAtIndex:[indexPath row]];
id cell = ...; //Now get your cell reference
//Now update your cell with the data from object
return cell;
【讨论】:
我认为您的回答应该对我有所帮助,但在哪里整合它将是我的下一个问题。你说要将它与我的 NSFetchedResultsController 及其委托方法集成,但是如何,我知道这是一个返回数组的完整方法,但我不知道我应该从哪里调用它......谢谢你的帮助 从任何需要访问数据的地方。-cellForRowAtIndexPath...
可能是一个不错的起点。
Marcus,当从 cellForRowAtIndexPath 方法调用你的方法时,我想我应该这样做:[self sortedSectionForIndex:sectionIndex]; sectionIndex 应该是要排序的部分。
马库斯,我做了如下: int indexPathSection = indexPath.section; [self sortedSectionForIndex:indexPathSection];在 cellForRowAtIndexPath 方法内部。它不会对放在 sortDescriptorWithkey 中的属性进行排序。
马库斯,你能帮我解决我之前的评论吗?我真的很感激。谢谢。【参考方案2】:
您可以在NSManagedObject
的awakeFromFetch
方法中规范化属性的时间组件。
- (void) awakeFromFetch
[super awakeFromFetch];
NSDateComponents* comps = [[NSCalendar currentCalendar] components:NSYearCalendarUnit|NSMonthCalendarUnit|NSDayCalendarUnit fromDate:self.itemDate];
self.itemDate = [[NSCalendar currentCalendar] dateFromComponents:comps];
此外,查看您的代码,您必须告诉NSFetchedResultsController
它应该基于什么分节符。为此,您可以在初始化时为分节符提供一个 keyPath。对于您的情况,不要使用sectionNameKeyPath:@"sectionIdentifier"
,而是使用第一个排序键:
_fetchedResultsController = [[NSFetchedResultsController alloc]initWithFetchRequest:fetchRequest managedObjectContext:context sectionNameKeyPath:@"itemDate" cacheName:nil];
【讨论】:
谢谢,但是按照您的建议更改 sectionNameKeyPath 不起作用,这些部分未显示... 我添加了有关如何在托管对象中标准化 itemDate 的时间分量的信息。以上是关于在表格视图部分中对核心数据对象进行排序的主要内容,如果未能解决你的问题,请参考以下文章
Swift UITableView(无部分)过滤到带有部分的表格视图