objective-c 带有搜索功能的 NSFetchedResultsController
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1418592/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
NSFetchedResultsController with search
提问by Guy
What is the best practice to filter the NSFetchedResultsControllerdata?
do i need to re-initialize it every time the searchbar's text changes?
过滤NSFetchedResultsController数据的最佳做法是什么?每次搜索栏的文本更改时我都需要重新初始化它吗?
I am using a UISearchDisplayControllersand i'm implementing:
我正在使用 aUISearchDisplayControllers并且我正在实施:
- (BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchString:(NSString *)searchString;
Thx.
谢谢。
采纳答案by dk.
How is Guy's answer code any different from the question? As far as I can guess, the filterContentForSearchText:scope method is called by the shouldReload methods?
Guy 的答案代码与问题有何不同?据我猜测, filterContentForSearchText:scope 方法是由 shouldReload 方法调用的吗?
Anyway, here's some similar code that I added in the CoreDataBooks sample to include search. Add a Search Display Controller in IB for the CoreDataBooks example. Then I added code to RootViewController.m as follows:
无论如何,这是我在 CoreDataBooks 示例中添加的一些类似代码以包含搜索。在 IB 中为 CoreDataBooks 示例添加一个搜索显示控制器。然后我将代码添加到 RootViewController.m 如下:
- (BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchString:(NSString *)searchString {
NSInteger searchOption = controller.searchBar.selectedScopeButtonIndex;
return [self searchDisplayController:controller shouldReloadTableForSearchString:searchString searchScope:searchOption];
}
- (BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchScope:(NSInteger)searchOption {
NSString* searchString = controller.searchBar.text;
return [self searchDisplayController:controller shouldReloadTableForSearchString:searchString searchScope:searchOption];
}
- (BOOL)searchDisplayController:(UISearchDisplayController *)controller shouldReloadTableForSearchString:(NSString*)searchString searchScope:(NSInteger)searchOption {
NSPredicate *predicate = nil;
if ([searchString length])
if (searchOption == 0) // full text, in my implementation. Other scope button titles are "Author", "Title"
predicate = [NSPredicate predicateWithFormat:@"title contains[cd] %@ OR author contains[cd] %@", searchString, searchString];
else
// docs say keys are case insensitive, but apparently not so.
predicate = [NSPredicate predicateWithFormat:@"%K contains[cd] %@", [[controller.searchBar.scopeButtonTitles objectAtIndex:searchOption] lowercaseString], searchString];
[fetchedResultsController.fetchRequest setPredicate:predicate];
NSError *error = nil;
if (![[self fetchedResultsController] performFetch:&error]) {
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
abort();
}
return YES;
}
PS. To answer Vivas, using a UISearchDisplayController it creates a new table view automatically for overlaying the filtered list. You can check which tableView is being used as shown in the docs, but in the simplest setup it just works because the fetchedResultsController is either showing a filtered version in the search's table view or showing all data in your table view.
附注。为了回答 Vivas,它使用 UISearchDisplayController 自动创建一个新的表视图来覆盖过滤列表。您可以检查正在使用哪个 tableView,如文档中所示,但在最简单的设置中,它仅起作用,因为 fetchedResultsController 要么在搜索的表视图中显示过滤版本,要么在表视图中显示所有数据。
回答by Guy
Appearantly this is a better way:
显然这是一个更好的方法:
- (void)filterContentForSearchText:(NSString*)searchText scope:(NSString*)scope
{
self.savedSearchTerm = searchText;
freshData = NO;
if (searchText !=nil)
{
NSPredicate *predicate =[NSPredicate predicateWithFormat:@"name contains[cd] %@", searchText];
[fetchedResultsController.fetchRequest setPredicate:predicate];
}
else
{
NSPredicate *predicate =[NSPredicate predicateWithFormat:@"All"];
[fetchedResultsController.fetchRequest setPredicate:predicate];
}
NSError *error = nil;
if (![[self fetchedResultsController] performFetch:&error]) {
// Handle error
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
exit(-1); // Fail
}
[self.tableView reloadData];
// [searchBar resignFirstResponder];
// [_shadeView setAlpha:0.0f];
}

