MySQL全字匹配–多个字

时间:2019-02-23 08:53:42

标签: php mysql sql regex

我已经阅读了很多类似的文章,但是都没有解决我的问题,这很可能是由于我缺乏足够的知识,所以请多多包涵。

我的术语词典中的搜索选项之一是“仅整个单词”。起初我在使用

WHERE ".$source." RLIKE '[[:<:]]".$keyword."[[:>:]]'

但是,当第一个$keyword或第二个WHERE ".$source." REGEXP '[[:<:]]".$keyword."[[:>:]]' 的单词全部不匹配时,则无法匹配整个单词。然后我发现了

WHERE ".$source." REGEXP '(^| )".$keyword."( |$)'

[[:<:]]

搜索these forums

我刚刚在PhpMyAdmin中测试了以上两种情况,发现前者执行时间为0.0740秒,而后者花费的时间是后者的两倍,即0.1440秒,所以我想我应该坚持使用前者。

最令我困扰的是结果的巨大差异,例如搜索一个单词(“工具”):

  1. 在PhpMyAdmin中使用[[:>:]](^| )字边界将返回34个结果。

  2. 在PhpMyAdmin中使用( |$)foreach($keywords as $keyword) { $query = $db->query("SELECT * FROM ".DICTIONARY_TABLE." " . "JOIN ".DICTIONARY_THEMES." ON ".DICTIONARY_TABLE.".theme_id = ".DICTIONARY_THEMES.".theme_id ". "LEFT JOIN ".DICTIONARY_DEFINITIONS." ON ".DICTIONARY_TABLE.".term_id = ".DICTIONARY_DEFINITIONS.".term_id ". "WHERE ".DICTIONARY_TABLE.".".$source." REGEXP '(^| )".$keyword."( |$)'". //"WHERE ".DICTIONARY_TABLE.".".$source." REGEXP '[[:<:]]".$keyword."[[:>:]]'". " ORDER BY ".DICTIONARY_TABLE.".theme_id, ".DICTIONARY_TABLE.".".$source.""); } 返回26个结果。

  3. 在我的PHP脚本中运行#1正则表达式会返回34个结果(这是正确的数字)。

这是整个MySQL块:

SELECT * FROM `asphodel_dictionary_terms` WHERE english REGEXP '[[:<:]]cutting[[:>:]]';
SELECT * FROM `asphodel_dictionary_terms` WHERE english REGEXP '[[:<:]]tool[[:>:]]'

我已经注释掉了我不使用的搜索选项。

现在,如果我尝试两个关键字,例如“切割工具”,我仍然在页面中获得34个结果。我不确定我是否在PhpMyAdmin中正确执行此操作:

(^| )

这将为“切割”返回44个结果,为“工具”返回34个结果。使用DICTIONARY_THEMES ...的查询分别返回37 + 26个结果。

任何能帮助我解决问题的反馈将不胜感激!

该数据库在主表中总共包含109,000个条目,在DICTIONARY_DEFINITIONS表中有82个主题,在{{1}}表中有727个条目。不是一个庞大的数据库,它也不会变得更大。

1 个答案:

答案 0 :(得分:1)

由于两个正则表达式不相同,因此得到的结果不同。

(^| )的含义是:字符串的开头或空格(( |$)在字符串的末尾具有相同的含义)。

[[:<:]][[:>:]]单词边界:从概念上讲,它是指分隔单词的字符,通常regex引擎将其解释为类似:除数字,字母或下划线。

因此,基本上第一种模式比第二种模式更具限制性(空格,字符串的开头和结尾是单词边界,但还有其他限制)。

如果要搜索的关键字不止一个,则需要重复正则表达式匹配项,例如:

WHERE 
    ".$source." RLIKE '[[:<:]]".$keyword1."[[:>:]]'
    OR ".$source." RLIKE '[[:<:]]".$keyword2."[[:>:]]'

或通过组合关键字创建新的正则表达式:

WHERE 
    ".$source." RLIKE '[[:<:]](".$keyword1.")|(".$keyword2.")[[:>:]]'

NB:出于搜索要求,您应该考虑使用MySQL Full Text Search,其主要目的是搜索完整的单词(不过有先决条件)。