I am trying to make a compound predicate for my core data search. So when the user enters text in the search bar, it will display results for anything that has that text in either the name, optionOne or optionTwo attributes.
I tried this:
- (void)searchBarSearchButtonClicked:(UISearchBar *)searchBar {
if (self.sBar.text !=nil) {
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"(name contains[cd] %@) || (optionOne contains[cd] %@) || (optionTwo contains[cd] %@)", self.sBar.text];
[fetchedResultsController.fetchRequest setPredicate:predicate];
}
NSError *error = nil;
if (![[self fetchedResultsController] performFetch:&error]) {
// Handle error
NSLog(@"Unresolved error %@, %@", error, [error userInfo]);
exit(-1); // Fail
}
[self.myTable reloadData];
[sBar resignFirstResponder];
}
But it just crashes without a descriptive reason. So I think I need to take these three predicates and somehow combine them:
NSPredicate *namePredicate = [NSPredicate predicateWithFormat:@"name contains[cd] %@", self.sBar.text];
NSPredicate *optionOnePredicate = [NSPredicate predicateWithFormat:@"optionOne contains[cd] %@", self.sBar.text];
NSPredicate *optionTwoPredicate = [NSPredicate predicateWithFormat:@"optionTwo contains[cd] %@", self.sBar.text];
Since you have 3
%@tokens in your string, you need to have 3self.sBar.textexpressions at the end.Alternatively, you could do something like this:
This is handier if you’re building this predicate a lot, because you can store the “template” predicate in an ivar. Parsing a predicate is not the snappiest of things, and using the template version means you’ll only have to parse it once (instead of every time the search bar’s text changes).