tags:

views:

462

answers:

3

I am currently using the following algorithm to search on my iPhone app:

NSRange range = [entry.englishEntry rangeOfString:searchText options:NSCaseInsensitiveSearch];
  if(range.location != NSNotFound)
  {
   [self.filteredListContent addObject:entry];
        }

The problem is that when I search for a word like 'crap' I also get results for words like 'scrap' which is irrelevant. I am unfamiliar with NSRange so what is the search algorithm for searching the whole word?

A: 

Instead of finding the range of a string, just do a case-insensitive compare and check if the result is NSOrderedSame

if([entry.english caseInsensitiveCompare:searchText] == NSOrderedSame){
  [self.filteredListContent addObject:entry];
}

This will compare the text with the whole word and not just look for the range.

lostInTransit
Thank You! However now it only picks up strings that begin with the searched word. (i.e. 'Hello World!" is not picked up by typing in 'World') I basically want to search strings for whole words anywhere in an Array of strings.
Kulpreet
In my knowledge, there is no method is the NSString class which would let you do that! Sorry.
lostInTransit
A: 

I just solved this problem by adding a simple category on NSString to do a word boundary search. Here's the code:

@interface NSString (FullWordSearch)

// Search for a complete word. Does not match substrings of words. Requires fullWord be present
// and no surrounding alphanumeric characters.
- (BOOL)containsFullWord:(NSString *)fullWord;

@end

@implementation NSString (FullWordSearch)

- (BOOL)containsFullWord:(NSString *)fullWord {
    NSRange result = [self rangeOfString:fullWord];
    if (result.length > 0) {
     if (result.location > 0 && [[NSCharacterSet alphanumericCharacterSet] characterIsMember:[self characterAtIndex:result.location - 1]]) {
      // Preceding character is alphanumeric
      return NO;
     }
     if (result.location + result.length < [self length] && [[NSCharacterSet alphanumericCharacterSet] characterIsMember:[self characterAtIndex:result.location + result.length]]) {
      // Trailing character is alphanumeric
      return NO;
     }
     return YES;
    }
    return NO;
}

@end
pix0r
+1  A: 

Yes you can search within words. You need to split the string into components first. Then loop through each one and compare them.

Something like that:

  NSArray *words = [entry.english componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceCharacterSet]];
  for (NSString *word in words)
  { 
      NSComparisonResult result = [word compare:searchText options:(NSCaseInsensitiveSearch|NSDiacriticInsensitiveSearch) range:NSMakeRange(0, [searchText length])];
      if (result == NSOrderedSame)
      {
        [self.filteredListContent addObject:entry];
        break;
      }
  }
Boon