1

目前我正在使用它来搜索我的字典数组(来自 plist 文件):

for(NSDictionary *wine in mainArray)
    {
        NSString *wineName = [wine objectForKey:@"name"];
        NSRange range = [wineName rangeOfString:searchText options:NSCaseInsensitiveSearch];
        if(range.location != NSNotFound)
            [searchArray addObject:wine];
    }

在这个问题中,我将以这个 plist 为例:

<array>
<dict>
  <key>name</key>
  <string>Banana One (Yellow)</string>
  <key>value</key>
  <string>1</string>
</dict>
<dict>
  <key>name</key>
  <string>Apple Two (White)</string>
  <key>value</key>
  <string>2</string>
</dict>
<dict>
  <key>name</key>
  <string>Pineapple Three (Orange)</string>
  <key>value</key>
  <string>3</string>
</dict>
<dict>
</array>

(不在乎值)

好的,当我将 UISearchBar 与 NSCaseInsensitiveSearch 一起使用时,我可以简单地搜索数组(ObjectForKey=@"name")而不考虑大小写。好的!

例如我可以搜索:@"banana"并找到:香蕉一号(黄色)

我可以搜索:@"two"并找到:Apple Two(White)

我可以搜索:@"banana一个”并找到:香蕉一号(黄色)

我还可以搜索:@"Orange"并找到:菠萝三(橙色)

但前提是搜索顺序正确

我无法搜索:@"One Banana"或者 我真的希望能够像这样搜索,也许使用关键字@"Yellow One"@"Yellow Banana"

也许是这样的?:

for(NSDictionary *wine in mainArray)
{
NSArray *myArray = [searchText componentsSeparatedByString:@" "];
    NSString *wineName = [wine objectForKey:@"name"];
    NSRange range = [wineName rangeOfString:myArray options:NSCaseInsensitiveSearch];
    if(range.location != NSNotFound)
        [searchArray addObject:wine];
}

我知道这真的行不通,但我想你知道我的意思吗?那么,如何能够搜索例如:@"one banana"并找到 :Banana One(黄色)

4

3 回答 3

1

我使用NSPredicate.

    NSArray *objects = @[@"Banana One",@"Apple Two"];
    NSString *searchString = @"one banana";
    NSArray *searchComoponents = [searchString componentsSeparatedByString:@" "];

    NSMutableString *format = [NSMutableString stringWithFormat:@"SELF CONTAINS[c] \"%@\"",[NSString stringWithFormat:@"%@",searchComoponents[0]]];
    for (int i = 1; i < searchComoponents.count; i++) {
        [format appendFormat:@" AND SELF CONTAINS[c] \"%@\"",[NSString stringWithFormat:@"%@",searchComoponents[i]]];
    }
    NSPredicate *predicate = [NSPredicate predicateWithFormat:[NSString stringWithFormat:@"%@",format]];
    NSArray *filtered = [objects filteredArrayUsingPredicate:predicate];

简单解释一下:SELF是数组中的当前对象,应该校对,CONTAINS看,左边的对象是否包含右边的对象,并[c]使其全部不区分大小写。因此,对于 searchString 中的每个关键字,您将条件添加到 predicateformat,这样最后,您应该有一个具有以下格式的 NSPredicate:SELF CONTAINS[c] object1 AND SELF CONTAINS[c] object2 .... 最后一个行使用这个 NSPredicate 创建一个过滤数组。有关 predicateFormat 的更多信息,请查看此处

于 2013-08-05T13:01:42.483 回答
1

解决了

感谢 DevFan 的回答!我需要编辑一些东西,例如 SELF 到 SELF.name 来指定我的字典数组中的键。

NSArray *searchComoponentsWithEmptyStrings = [searchText componentsSeparatedByString:@" "];
        NSMutableArray *searchComoponents = [searchComoponentsWithEmptyStrings mutableCopy];
        [searchComoponents removeObject:@""]; //remove empty strings from the array (only works with NSMutableArray)

        NSMutableString *format = [NSMutableString stringWithFormat:@"SELF.name CONTAINS[c] '%@'",[NSString stringWithFormat:@"%@",searchComoponents[0]]];
        for (int i = 1; i < searchComoponents.count; i++) {
            [format appendFormat:@"AND SELF.name CONTAINS[c] '%@'",[NSString stringWithFormat:@"%@",searchComoponents[i]]];
        }
        NSPredicate *predicate = [NSPredicate predicateWithFormat:[NSString stringWithFormat:@"%@",format]];
        searchArray = [mainArray filteredArrayUsingPredicate:predicate];

现在我也可以搜索@“banana”(末尾有空格),仍然可以找到香蕉一号(黄色)

于 2013-08-06T07:15:45.330 回答
0

也许您应该将 NSString "Banana One (Yellow)" 拆分为一个数组 ("Banana", "One", "(Yellow)") 并检查其中一个是否包含在您的搜索文本中。

    NSString *searchText = @"One";
    NSString *txt = @"Banana One (Yellow)";
    NSArray* splitString = [txt componentsSeparatedByString:@" "];
    for(int i = 0; i < [splitString count]; i++){
        if([[splitString objectAtIndex:i] rangeOfString:searchText].location != NSNotFound) {
            return txt;
        }
    }
于 2013-08-05T11:56:04.247 回答