我一直在使用核心数据创建iPhone应用程序。
首先,使用NSFetchedResultsController和UISearchDisplayController一起获取结果是否有意义?你会推荐别的吗?
我一直在尝试很长时间组合NSFetchedResultController和UISearchDisplayController。我一直在考虑在(BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchScope:(NSInteger)searchOption
方法中将NSPredicate设置为UIViewController的NSFetchedResultController。但这并没有那么好。
那么,您知道如何为我的问题实施解决方案吗?非常感谢您发布答案或指向优秀教程的链接。
修改
这是我的代码。 UISearchDisplayDelegate方法调用应在NSFetchedResultController中设置谓词的方法(void)filterContentForSearchText:(NSString*)searchText scope:(NSString*)scope
。我还添加了NSFetchedResultController的代码。
- (BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchString:(NSString *)searchString
{
[self filterContentForSearchText:searchString scope:
[[self.searchDisplayController.searchBar scopeButtonTitles] objectAtIndex:[self.searchDisplayController.searchBar selectedScopeButtonIndex]]];
// Return YES to cause the search result table view to be reloaded.
return YES;
}
- (BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchScope:(NSInteger)searchOption
{
[self filterContentForSearchText:[self.searchDisplayController.searchBar text] scope:
[[self.searchDisplayController.searchBar scopeButtonTitles] objectAtIndex:searchOption]];
// Return YES to cause the search result table view to be reloaded.
return YES;
}
- (void)filterContentForSearchText:(NSString*)searchText scope:(NSString*)scope
{
NSString *query = self.searchDisplayController.searchBar.text;
if (query && query.length) {
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"Name contains[cd] %@", query];
[fetchedResultsController.fetchRequest setPredicate:predicate];
}
NSError *error = nil;
if (![[self fetchedResultsController] performFetch:&error]) {
// Handle error
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
exit(-1); // Fail
}
}
- (NSFetchedResultsController *)fetchedResultsController {
if (fetchedResultsController != nil) {
return fetchedResultsController;
}
/*
Set up the fetched results controller.
*/
// Create the fetch request for the entity.
NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
// Edit the entity name as appropriate.
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Event" inManagedObjectContext:managedObjectContext];
[fetchRequest setEntity:entity];
// Set the batch size to a suitable number.
[fetchRequest setFetchBatchSize:20];
// Edit the sort key as appropriate.
NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"timeStamp" ascending:NO];
NSArray *sortDescriptors = [[NSArray alloc] initWithObjects:sortDescriptor, nil];
[fetchRequest setSortDescriptors:sortDescriptors];
// Edit the section name key path and cache name if appropriate.
// nil for section name key path means "no sections".
NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:managedObjectContext sectionNameKeyPath:nil cacheName:@"Root"];
aFetchedResultsController.delegate = self;
self.fetchedResultsController = aFetchedResultsController;
[aFetchedResultsController release];
[fetchRequest release];
[sortDescriptor release];
[sortDescriptors release];
return fetchedResultsController;
}
答案 0 :(得分:21)
瞥见你的代码吧。我遇到了使用此方法更改搜索的问题。修复:清除缓存!
假设您启动了获取的结果控制器,如下所示。请注意cacheName属性。
NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:[self fetchRequest] managedObjectContext:managedObjectContext sectionNameKeyPath:nil cacheName:@"UserSearch"];
在更改谓词时,只需添加:
[NSFetchedResultsController deleteCacheWithName:@"UserSearch"];
像魔法一样,它会很好地运作。
您还需要监控搜索显示控制器何时结束搜索,并擦除谓词。
虽然这个帖子看起来已经死了,但我在google上找到了它,所以也许那里有人会使用它。 :)
答案 1 :(得分:7)
根据文档,您要么想使用谓词将结果过滤到数组中,要么重新初始化fetchedResultsController。
重要提示:您不得修改 你有了获取请求 初始化控制器。对于 例如,你不能改变 谓词或排序顺序。
(我会评论闲置的答案,但我是无业力的。)
答案 2 :(得分:1)
听起来你只对获取和显示对象感兴趣。在这种情况下,您不使用搜索显示控制器。搜索显示控制器与搜索栏一起使用,以帮助允许用户输入的内容文本搜索。
通常,您使用获取的结果控制器来帮助您实现表视图数据源和委托方法。此外,您还为获取的结果控制器创建并使用获取请求。这是所有样板(请参阅Apple在您选择“使用核心数据进行存储”选项创建新项目时提供的模板代码。)
您可以在获取请求中创建并指定谓词。这将允许您过滤表格显示的对象。例如:
// only fetch objects with myAttribute set to someValue
NSPredicate *pred = [NSPredicate predicateWithFormat:@"myAttribute == %@",someValue];
[fetchRequest setPredicate:pred];