MySQL之全文索引二三事

MySQL全文索引用于提升文本搜索效率,支持模糊搜索和多词搜索。创建全文索引后,使用MATCHAGAINST执行查询。ngram解析器适用于中文等无明显分隔符的文本,通过设置ngram_token_size调整分词大小。全文搜索有两种模式:自然语言模式(默认,处理相关性)和布尔模式(精确控制搜索条件)。全文索引优于LIKE%%操作,提供更好的查询性能。
摘要由CSDN通过智能技术生成

全文索引

MySQL全文索引是一种用于快速搜索文本字符串的索引,在MySQL数据库中,它可以用来提高文本搜索的效率。全文索引不同于普通索引,普通索引只是对列值进行排序,而全文索引则会对列的内容进行分词,并且对每个分词建立索引,从而可以在文本中进行模糊搜索、部分匹配和多词搜索等操作。

创建全文索引的语法

创建全文索引的语法如下:

CREATE FULLTEXT INDEX index_name
ON table_name (column_name)
[WITH PARSER parser_name]

其中,index_name是要创建的索引的名称,table_name是要创建索引的表的名称,column_name是要在其中创建索引的列的名称。WITH PARSER子句是可选的,并且可以用于指定在创建索引时要使用的解析器

全文索引只能用于CHAR、VARCHAR、TEXT和BLOB类型的字段。此外,在MySQL 5.6版本以前,全文索引只支持MyISAM存储引擎,而在MySQL 5.6版本以后,InnoDB存储引擎也支持全文索引。

使用全文索引进行查询

创建全文索引后,可以使用MATCH AGAINST语句来执行全文搜索查询。

SELECT * FROM table_name WHERE MATCH(column_name) AGAINST('keyword');

ngram解析器

内置的FULLTEXT解析器通过查找特定的分隔符来确定单词的开始和结束位置;例如:(空格),(逗号),和.(点号)。如果单词之间没有分隔符(例如中文),则内置的FULLTEXT解析器无法确定单词的开始或结束位置。

我们可以使用ngram解析器插件(用于中文、日文或韩文)或MeCab解析器插件(用于日文)创建FULLTEXT索引。

ngram是给定文本序列中n个字符的连续序列。ngram解析器将文本序列标记为连续的n个字符序列。例如,您可以使用ngram全文解析器将“abcd”标记为不同的n值。

n=1: 'a', 'b', 'c', 'd'
n=2: 'ab', 'bc', 'cd'
n=3: 'abc', 'bcd'
n=4: 'abcd'

这里的n事实上是ngram指定的令牌大小(token size),Ngram令牌大小可以使用ngram_token_size配置选项进行配置,该选项的最小值为1,最大值为10。

需要注意的是:

  • 1.修改ngram_token_size需要重启mysql服务器。

  • 2.修改了ngram_token_size之后,我们需要重建fulltext索引,一般我们采用删了重加的方式重建。

  • 3.对于使用ngram解析器的FULLTEXT索引,忽略以下最小和最大字长配置选项:innodb_ft_min_token_size, innodb_ft_max_token_size, ft_min_word_len和ft_max_word_len。这些参数分别是innodb、myIsam引擎在使用非ngram分词时对应的设置令牌大小的参数。

ngram_token_size设置为要搜索的最大令牌的大小。如果我们需要只搜索单个字符,请将ngram_token_size设置为1。

比如我们要使用全文索引,查询name字段中包含“刘”字的记录。

创建使用ngram分词的全文索引:

alter table `user` add fulltext index idx_name (name) with parser ngram

使用Match Against语法进行查询:

SELECT * FROM `uuc_business_user` where MATCH(name) AGAINST('刘')

需要注意的是,我是使用单个汉字(刘)进行查询的,这个时候如果想要查询到结果,需要将ngram_token_size设置为1,如果ngram_token_size的值是大于1的数,将查询不到任何记录。如果我们要支持搜索单个字符,记住需要将ngram_token_size设置为1。

ngram_token_size设置为1之后,使用大于1个的汉字进行搜索时,mysql会将汉字拆分为多个单个汉字分别进行搜索,然后将结果进行合并。

比如使用 MATCH(name) AGAINST('刘娅')进行查询时,得到的结果,会如下所示:

如果想要查询结果,同时包含“刘”和“娅”,可以使用如下语法进行查询:

SELECT * FROM uuc_business_user WHERE MATCH (name) AGAINST ('"刘娅"' IN BOOLEAN MODE);

上面的语句中使用了布尔模式,包含在双引号内的搜索词语“刘娅”被看作一个短语,表示必须同时包含这两个词语,即只有完全匹配“刘娅”这个词语的文档才会被返回。在布尔模式下,使用双引号括起来的搜索词语表示一个短语,这个短语必须完全匹配才能返回结果。因此,这个查询只会返回包含完整短语“刘娅”的文档,不会返回包含“刘”和“娅”这两个词语的文档。

而如果不加in BOOLEAN MODE,则默认是使用了自然语言模式,MySQL会使用内置的自然语言处理技术对搜索查询进行分词和停用词处理,并根据每个词语在文档中的重要性对文档进行打分。在自然语言模式下,使用双引号括起来的搜索词语表示一个短语,但并不要求这个短语必须完全匹配。因此,这个查询将返回包含“刘”和“娅”这两个词语的文档,不一定是完全匹配“刘娅”这个短语的文档。

自然模式和布尔模式

在MySQL中,全文搜索支持两种主要的查询模式:自然语言模式和布尔模式。这两种模式的主要区别在于它们如何处理搜索查询和返回结果。

自然模式 (IN NATURAL LANGUAGE MODE)

全文搜索中的自然语言模式是默认模式,它使用自然语言处理技术来解析搜索查询并返回最相关的结果。自然语言模式会对搜索查询进行分词和停用词处理,并根据每个词语在文档中的重要性对文档进行打分。然后,MySQL会根据文档的得分对搜索结果进行排序,并返回最相关的文档。

例如,以下查询将在自然语言模式下搜索包含“刘”和“娅”的文档,并按照相关性进行排序:

SELECT * FROM users
WHERE MATCH(name) AGAINST('刘 娅' IN NATURAL LANGUAGE MODE);

布尔模式(IN BOOLEAN MODE)

全文搜索中的布尔模式允许用户使用布尔运算符(AND、OR、NOT) 来组合搜索条件,并通过对文档进行匹配来确定文档是否符合查询条件。在布尔模式下,MySQL会将搜索查询视为布尔表达式,并使用布尔运算符来确定每个文档是否符合查询条件。

例如,以下查询将在布尔模式下搜索包含“刘”和“娅”的文档:

SELECT * FROM users
WHERE MATCH(name) AGAINST('+刘 +娅' IN BOOLEAN MODE);

在布尔模式下,“+”符号表示必须包含该词语,“-”符号表示不包含该词语,“|”符号表示或者。这个查询将返回包含“apple”和“iphone”两个词语的文档。

需要注意的是,自然语言模式和布尔模式都有各自的优点和缺点。自然语言模式通常更易于使用和理解,但可能会导致一些不准确的结果。布尔模式更灵活,可以更精确地控制搜索条件,但需要更多的查询语法知识。在使用全文搜索时,应根据具体情况选择合适的查询模式。

全文索引与 like "%%"

全文索引和LIKE "%%"是两个不同的文本搜索方法,它们在实现和性能上有很大的差异。

全文索引是一种特殊类型的索引,用于对文本字段进行全文搜索,它可以支持模糊搜索、部分匹配和多词搜索等操作。全文索引可以显著提高文本搜索的性能和效率,特别是在处理大量文本数据时。

与此不同,LIKE "%%"是一种基于通配符的模式匹配操作,可以在文本字段中查找包含指定字符串的记录。但是,LIKE "%%"操作通常会导致全表扫描,并且性能较低,特别是在处理大量数据时。

因此,全文索引通常比LIKE "%%"操作更快、更有效。在需要对文本字段进行搜索时,应该尽量使用全文索引,而不是LIKE "%%"操作,以获得更好的查询性能和效率

总结

mysql使用全文索引来提高文本搜索的效率。我们可以使用FULLTEXT关键字来声明一个全文索引列,创建全文索引后,可以使用MATCH AGAINST语句来执行全文搜索查询。 我们需要使用ngram分词器来支持中文全文搜索。ngram_token_size用来指定令牌大小。全文搜索支持两种主要的查询模式:自然语言模式和布尔模式,自然语言模式通常更易于使用和理解,但可能会导致一些不准确的结果。布尔模式更灵活,可以更精确地控制搜索条件,但需要更多的查询语法知识。

参考: https://dev.mysql.com/doc/refman/8.0/en/fulltext-fine-tuning.html

 

图片

点个“赞 or 在看” 你最好看!

喜欢,就关注我吧!

图片

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值