33
-(BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
  [self.map removeAnnotations:self.map.annotations];
  if ([textField isEqual:self.searchText]) {
      NSPredicate *bPredicate = 
      [NSPredicate predicateWithFormat:@"name contains[c],  %@",self.searchText.text];

      self.filteredArray = [self.hotelArray filteredArrayUsingPredicate:bPredicate];
      NSLog(@" HEARE %@",self.filteredArray);
      [self markAllHotels];
  }
  return YES;
}

hotelArray and filteredArray are NSArrays.

hotelArray has objects of type hotel where hotel has a property name.

Problem : I want to filter hotelArray according to hotel.name when hotel.name matches text entered in searchText [text field], but I am getting an empty self.filteredArray.

3
  • Check this one stackoverflow.com/questions/1473973/… Commented Oct 30, 2013 at 7:39
  • Your question is missing. What problems do you exactly have with your posted code? Commented Oct 30, 2013 at 7:41
  • @Vishwa Patel that code is not working for me . using ANY is crashing the simulator. Commented Oct 30, 2013 at 7:53

5 Answers 5

72

Try following lines, and make sure properyName is case sensitive. and you have placed , in predicate format, thats why its not working. just replace your code with following.

Objective C

NSPredicate *bPredicate = [NSPredicate predicateWithFormat:@"SELF.name contains[cd] %@",self.searchText.text];
self.filteredArray = [self.hotelArray filteredArrayUsingPredicate:bPredicate];
NSLog(@"HERE %@",self.filteredArray);

Swift

var bPredicate: NSPredicate = NSPredicate(format: "SELF.name contains[cd] %@", self.searchText.text)
self.filteredArray = self.hotelArray.filteredArrayUsingPredicate(bPredicate)
NSLog("HERE %@", self.filteredArray)

Using swift filter

var searchText = "Galaxy"

let filteredArray = hotelArray.filter { $0["name"] == searchText }
print("** Result ** \n\(filteredArray)")

Swift 3.0

let arrEmp = [["name": "James", "age" : 27, "city" : "New york"],
                   ["name": "Johnson", "age" : 24, "city" : "London"],
                   ["name": "Alex", "age" : 28, "city" : "Newark"],
                   ["name": "Mark", "age" : 25, "city" : "Paris"],
                   ["name": "Steve", "age" : 25, "city" : "Silicon Valley"],
                   ["name": "Lary", "age" : 28, "city" : "New york"]]

// *** Filter by Name exact match ***
var filterByName = arrEmp.filter { $0["name"] == "Mark" }
print("filterByName \(filterByName)")

// *** Filter by Age ***
var filterByAge = arrEmp.filter { $0["age"] as! Int >  25 }
print("filterByAge \(filterByAge)")

Swift 4.0

var filterByName = arrEmp.filter
do {
    $0["name"] == "Mark"
}
print("filterByName filterByName)")

var filterByAge = arrEmp.filter
do {
    $0["age"] as! Int > 25
}
print("filterByAge filterByAge)")
Sign up to request clarification or add additional context in comments.

4 Comments

[NSString "sometext%i",4] IOS makes it number not string that was the error .
@Anz are you filtering array of dictionary? Given code is tested on Swift 3.0
@DipenPanchasara Yes it is
You can post a question with your data and other information, then one can provide solution
5

Based on your information, this is your situation:

self.hotelArray      // Array in which we perform a search
self.filteredArray   // Result array
name                 // Property of the object used for the predicate

This predicate should work for you:

NSString *searchText = self.searchText.text;
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"self.name contains[c] %@", searchText];
self.filteredArray = [self.hotelArray filteredArrayUsingPredicate:predicate];

Comments

2

Checkout this library

https://github.com/BadChoice/Collection

It comes with lots of easy array functions to never write a loop again

So you can just do:

NSArray* hotels = [self.hotelArray filter:^BOOL(Hotel *hotel) {
    [return hotel.name isEqualToString:searchText];
}];

or simply

NSArray* hotels = [self.hotelArray where:@"name" is:searchText];

:)

Comments

1

This is the predicate method that might work for you.

-(void)filterContentForSearchText:(NSString*)searchText scope:(NSString*)scope
{
    [filteredContactArray removeAllObjects];

    NSArray *tempArray = [hotelArray filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"name contains[c] %@ OR name contains[cd] %@",searchText]];

    filteredArray = [NSMutableArray arrayWithArray:tempArray];//if you want the filtered array to be mutable or tempArray will work as as desired by you.
}

contains[c]- means the predicate with case sensitive. contains[cd]- case insensitive string

Comments

0

I'm not sure if this is what you want to do :

-(NSArray*)searchString:(NSString*)stringToSearch inArray:(NSArray*)myArray
{
    NSMutableArray* filtredArray = [[NSMutableArray alloc] init];
    for (NSString* elmnt in myArray)
    {
        if ([elmnt rangeOfString:stringToSearch].location != NSNotFound) [fitredArray addObject:elmnt];
    }
    return filtredArray;
}

2 Comments

i don't wanna loop through elements.
i wanna use filteredArrayUsingPredicate or something similar

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.