如何使用 NSPredicate 在字符串中查找开头的单词?

Posted

技术标签:

【中文标题】如何使用 NSPredicate 在字符串中查找开头的单词?【英文标题】:How to find beginswith word in a string using NSPredicate? 【发布时间】:2010-08-28 09:41:13 【问题描述】:

我正在寻找有关如何格式化 NSPredicate 以在文本字符串中搜索正确单词的解决方案。 目前我正在使用此代码:

NSPredicate *predicate = [NSPredicate predicateWithFormat:
                          @"(content CONTAINS[c] %@)", word];

但是如果单词很短,它会返回错误的结果,例如: 如果单词是'ail',它将返回所有包含这3个字母的单词的字符串。但是我不需要这样的抽象搜索,那么如何在字符串中搜索单词'beginswith'我的单词?

【问题讨论】:

通常建议同时搜索变音符号不敏感。这是通过CONTAINS[cd] 完成的;添加d 【参考方案1】:

只需使用BEGINSWITH 而不是CONTAINS

编辑

如果您需要在字符串的每个单词中进行搜索,WWDC 2010 的一次演讲中提出了一种技术。基本思想是创建一个单独的实体 Word,其中包含一个单词和一个包含对象(您正在搜索的实体)的引用。然后您在Word 实体上进行搜索并返回与找到的单词相关的对象。

查询将如下所示(假设您的实体与 Word 之间存在多对一关系:“ANY words BEGINSWITH[c] %@”

这意味着您必须在创建对象时设置单词。

【讨论】:

感谢您抽出宝贵时间,但我说的是字符串,而不是单词。如果我将使用 beginwith 它将返回所有以我的单词开头的字符串,但我需要返回包含单词的字符串,以我的单词开头... 那么你需要的是“内容中的任何单词都以XX开头”之类的东西吗? 是的,像这样。但它应该返回整个字符串。问题是我需要在 ny Core Data 食谱中按食谱标题查找其中一种成分。例如,如果我搜索苹果,我需要找到标题为“Fuji Apples Tarte Tatin”的食谱。 我编辑了我的答案,为您提供了一个示例,说明如何做到这一点。这是来自 WWDC 2010 Core Data 演讲,所以如果您是注册开发者,您可以观看视频。 @Azia 我建议在这种情况下使用“CONTAINS”【参考方案2】:

首先使用BEGINSWITH 搜索“Foo”,这会找到字符串的开头

"Foo Word1 Word2", "Foo OtherWord1 OtherWord2" (will find 2)

而不是 CONTAINS 代表“Foo”(注意 Foo 之前的空格),这将为您提供以“Foo”开头的单词并以空格为首

"Word1 Foo Word", "Some OtherWord FooWord", "Misc    FooXWord" (will find 3)

谓词:

NSPredicate *predicate = [NSPredicate predicateWithFormat:
                          @"(content BEGINSWITH[c] %@) OR (content CONTAINS[c] %@)", word, [NSString stringWithFormat:@" %@", word]];

【讨论】:

这就是我想要的......改变聪明的答案......谢谢老兄【参考方案3】:

如果你的文本在单词之间包含一些标点符号,你可以使用这个谓词:

NSPredicate *predicate = [NSPredicate predicateWithFormat:
                              @"(name BEGINSWITH[c] %@) OR (name MATCHES[c] %@)", 
                              query,
                              [NSString stringWithFormat:@".*[^\\w]%@.*", query]];

【讨论】:

哇!在我看到这个之前,我认为标记化是唯一的解决方案。 这比公认的答案更容易,而且可能更好。 正则表达式很慢,最好搜索以空格为前缀的常规字符串【参考方案4】:

我遇到了同样的问题,起初我认为您的回答可以帮助我,但他们没有。这个对我有帮助,所以...看看:

NSString *matchString =  [NSString stringWithFormat: @".*\\b%@.*",searchText];
NSString *predicateString = @"keyword MATCHES[c] %@";
NSPredicate *predicate =[NSPredicate predicateWithFormat: predicateString, matchString];

【讨论】:

哇,这个效果非常好。我的一些话在( ) 之间,例如Hello (world),您的解决方案与 searchText == "w" 匹配。谢谢。如果你有时间,请解释一下这是如何工作的,我不熟悉\b【参考方案5】:

尝试使用复合:

NSCompoundPredicate *bPredicate =  [NSCompoundPredicate orPredicateWithSubpredicates:@[[NSPredicate predicateWithFormat:@"content BEGINSWITH[cd] %@",_SearchBar.text], [NSPredicate predicateWithFormat:@"content CONTAINS[cd] %@", _SearchBar.text]]];

【讨论】:

以上是关于如何使用 NSPredicate 在字符串中查找开头的单词?的主要内容,如果未能解决你的问题,请参考以下文章

使用 NSPredicate contains 在 coredata 实体的字段中查找字符

创建一个 NSPredicate 来查找长度大于 N 的元素

NSPredicate 与 NSString:查找超字符串哪个更好/更快?

核心数据:在两个实体中查找的 NSPredicate

核心数据和 NSPredicate

iOS核心数据如何使用NSPredicate根据一对多的子属性查找父对象?