mysql 中文全文搜索,mysql自带的中文检索

在MySQL 5.7.6之前,全文索引只支持英文全文索引,不支持中文全文索引,需要利用分词器把中文段落预处理拆分成单词,然后存入数据库。
从MySQL 5.7.6开始,MySQL内置了ngram全文解析器,用来支持中文、日文、韩文分词。
本文使用的MySQL 版本是5.7.22,InnoDB数据库引擎。

mysql原生全文解析器(ngram)

MySQL 中使用全局变量ngram_token_size来配置ngram中n的大小,它的取值范围是1到10,默认值是2。通常ngram_token_size设置为要查询的单词的最小字数。如果需要搜索单字,就要把ngram_token_size设置为1。在默认值是2的情况下,搜索单字是得不到任何结果的。因为中文单词最少是两个汉字,推荐使用默认值2。

全局变量ngram_token_size的两种设置方法:
1、启动mysqld命令时  

mysqld --ngram_token_size=2

2、修改MySQL配置文件

[mysqld] 
ngram_token_size=2

创建全文索引

1、创建表的同时创建全文索引

CREATE TABLE articles (
    id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
    title VARCHAR (200),
    body TEXT,
    FULLTEXT (title, body) 
) ENGINE = INNODB;

2、通过 alter table 的方式来添加

ALTER TABLE articles ADD FULLTEXT INDEX ft_index (title,body) ;

 

 

假如数据库有如下数据:

mysql 中文全文搜索,mysql自带的中文检索_第1张图片

 查询方法:select * from  articles where MATCH  (title,body)  AGAINST  ('布衣');

 

mysql全文检索模式:

常用的全文检索模式有两种:
1、自然语言模式(NATURAL LANGUAGE MODE) ,自然语言模式是MySQL 默认的全文检索模式。自然语言模式不能使用操作符,不能指定关键词必须出现或者必须不能出现等复杂查询。
2、BOOLEAN模式(BOOLEAN MODE),BOOLEAN模式可以使用操作符,可以支持指定关键词必须出现或者必须不能出现或者关键词的权重高还是低等复杂查询。

MySQL中文全文索引查询:

 select * from  articles where MATCH (title,body) AGAINST ('布衣');

MySQL中文全文索引查询,根据匹配度权重来排序

select *,match(title,body) AGAINST ('{$search}') as score from articles  order  by score desc

mysql全文搜索语法(BOOLEAN MODE

SELECT * FROM articles WHERE MATCH (title,body) AGAINST ('+先帝 -出师表' IN BOOLEAN MODE); 

解析:+ 表示AND,即必须包含。- 表示NOT,即不包含。

 

SELECT * FROM articles WHERE MATCH (title,body) AGAINST ('先帝 诸葛亮' IN BOOLEAN MODE);

解析:先帝和诸葛亮之间是空格,空格表示OR,即至少包含先帝、诸葛亮中的一个即可。

 

SELECT * FROM articles WHERE MATCH (title,body) AGAINST ('+先帝 赏罚' IN BOOLEAN MODE);

解析:必须包含“先帝 ”,但是如果同时也包含“ 赏罚 ”则会获得更高的权重。

 

SELECT * FROM articles WHERE MATCH (title,body) AGAINST ('+先帝 ~布衣' IN BOOLEAN MODE);  

解析:~ 是我们异或运算符。返回的记录必须包含先帝,但是如果同时也包含“ 布衣 ”会降低权重。但是它没有 +先帝  -布衣严格,因为后者如果包含‘’布衣‘’压根就不返回。

 

mysql全文搜索注意事项:

  • 只能在类型为CHAR、VARCHAR或者TEXT的字段上创建全文索引。
  • 全文索引只支持InnoDB和MyISAM引擎。
  • MATCH (columnName) AGAINST ('keywords')。MATCH()函数使用的字段名,必须要与创建全文索引时指定的字段名一致。如上面的示例,MATCH (title,body)使用的字段名与全文索引ft_articles(title,body)定义的字段名一致。如果要对title或者body字段分别进行查询,就需要在title和body字段上分别创建新的全文索引。
  • MATCH()函数使用的字段名只能是同一个表的字段,因为全文索引不能够跨多个表进行检索。
  • 如果要导入大数据集,使用先导入数据再在表上创建全文索引的方式要比先在表上创建全文索引再导入数据的方式快很多,所以全文索引是很影响TPS的。

 

参考文章:

https://www.jianshu.com/p/c48106149b6a      

http://m.lao8.org/a1602

MySQL 5.7新特性系列一  

MySQL 5.7新特性系列二  

MySQL 5.7新特性介绍 

MySQL5.7中InnoDB不可不知的新特性

 

 

 

 

 

 

你可能感兴趣的:(mysql)