MySQL 全文索引使用指南


Posted in MySQL onMay 25, 2021

全文索引需要特殊的查询语法。有没有索引都可以进行全文检索,但是存在索引时会提高匹配的速度。全文索引的索引通过特殊的结构存储以便于找到文档中包含搜索关键字对应的内容。在我们日常生活中,最常见的全文检索就是网络搜索引擎。虽然,网络搜索引擎的数据里十分庞大,并且通常也不会使用关系型数据库,但是原理是相似的。

全文索引支持通过基于字符(CHAR、VARCHAR 和 TEXT 类型的列)的检索,也可以支持自然语言模式(Natural Language Mode, 默认)和布尔模式 (Boolean Mode)。例如我们搜索“数据库引擎”的时候,内容中包括“数据库”、“引擎”和“数据库引擎”的内容都会检索出来。全文索引的实现有大量的限制,而且十分复杂。但是由于内置在MySQL服务端,而且对很多应用都能够满足要求,因此被广泛使用。

在MySQL5.6之前的版本中,只有 MyISAM 存储引擎支持全文索引。创建全文索引需要指定列标记为全文索引,如下面的 content 列。

CREATE TABLE t_news (
	id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
	content TEXT,
	author VARCHAR(32),
	title VARCHAR(128),
  FULLTEXT (content)
) ENGINE=InnoDB;

MySQL 5.6以前对中文搜索支持不是太好,需要自己进行分词后将段落预处理拆分成单词在入库。MySQL5.7.6后才有了内置的分词器 ngram。ngram 支持设置设置分词的长度,可以将中文按长度拆分为不同的单词(虽然不太智能,但满足大部分场景)。可以通过 MySQL 的全局变量ngram_token_size设置分词长度,默认是2,支持1-10可选。对于上面的例子,需要指定分词器构建全文索引。

CREATE TABLE t_news (
  id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
	content TEXT,
	author VARCHAR(32),
	title VARCHAR(128),
  FULLTEXT KEY idx(content) WITH PARSER ngram
) ENGINE=InnoDB;

插入一条数据测试。

INSERT INTO `t_news` 
(`id`, `content`, `author`, `title`) 
VALUES ('1', '我有一个数据库和引擎', '岛上码农', '数据库引擎');

在简单的模糊搜索中可以使用 LIKE 来完成,而对于全文检索需要使用如下方式的语句:

SELECT * FROM t_news 
WHERE MATCH (content) AGAINST ('数据 引擎' IN NATURAL LANGUAGE MODE)

通过这种方式可以检索出刚刚插入的内容,而如果使用 LIKE 是没法完成的。也支持使用相关性排序,再插入一条数据:

INSERT INTO `t_news`
(`id`, `content`, `author`, `title`) 
VALUES (2,'我有一个数据库','岛上码农','数据库')

然后执行排序查询:

SELECT *, MATCH (content) AGAINST ('数据 引擎' ) AS relevance
FROM t_news 
WHERE MATCH (content) AGAINST ('数据 引擎' ) 
ORDER BY relevance ASC

这里将匹配值作为一列查询,以便使用其别名进行排序。相关性越高,对应的 relevance 值越大,因此可以用作排序。入股不相关,那么 relevance 的值为0。

布尔模式可以做更多的控制,例如包括使用+号保留匹配结果和使用-号排除匹配结果,下面的就匹配了数据,而排除了包含引擎的数据。更多操作符可以参考 MySQL 的官方文档:全文索引操作符

SELECT * FROM t_news 
WHERE MATCH (content) AGAINST ('+数据* -引擎' IN BOOLEAN MODE);

以上就是MySQL 全文索引使用指南的详细内容,更多关于MySQL 全文索引的资料请关注三水点靠木其它相关文章!

MySQL 相关文章推荐
Mysql Online DDL的使用详解
May 20 MySQL
my.ini优化mysql数据库性能的十个参数(推荐)
May 26 MySQL
Mysql中存储引擎的区别及比较
Jun 04 MySQL
MySQL外键约束(FOREIGN KEY)案例讲解
Aug 23 MySQL
防止web项目中的SQL注入
Dec 06 MySQL
Mysql分库分表之后主键处理的几种方法
Feb 15 MySQL
MySQL多表查询机制
Mar 17 MySQL
mysql 8.0.27 绿色解压版安装教程及配置方法
Apr 20 MySQL
深入理解MySQL中MVCC与BufferPool缓存机制
May 25 MySQL
SQL语句中EXISTS的详细用法大全
Jun 25 MySQL
MySQL事务的隔离级别详情
Jul 15 MySQL
MySQL生成千万测试数据以及遇到的问题
Aug 05 MySQL
52条SQL语句教你性能优化
May 25 #MySQL
简单了解 MySQL 中相关的锁
mysql在项目中怎么选事务隔离级别
.Net Core导入千万级数据至Mysql的步骤
May 24 #MySQL
MySQL大小写敏感的注意事项
May 24 #MySQL
MySQL 使用事件(Events)完成计划任务
May 24 #MySQL
MySQL触发器的使用
May 24 #MySQL
You might like
PHP无限分类代码,支持数组格式化、直接输出菜单两种方式
2011/05/18 PHP
php中的比较运算符详解
2013/10/28 PHP
php GUID生成函数和类
2014/03/10 PHP
PHP读取CURL模拟登录时生成Cookie文件的方法
2014/11/04 PHP
php开发工具有哪五款
2015/11/09 PHP
PHP 接入微信扫码支付总结(总结篇)
2016/11/03 PHP
PHP+Ajax实现的检测用户名功能简单示例
2019/02/12 PHP
JavaScript constructor和instanceof,JSOO中的一对欢喜冤家
2009/05/25 Javascript
JavaScript之HTMLCollection接口代码
2011/04/27 Javascript
js查错流程归纳
2012/05/04 Javascript
任意Json转成无序列表的方法示例
2016/12/09 Javascript
浅谈javascript alert和confirm的美化
2016/12/15 Javascript
nodejs个人博客开发第五步 分配数据
2017/04/12 NodeJs
浅谈Angular HttpClient简单入门
2018/05/04 Javascript
jQuery插件实现的日历功能示例【附源码下载】
2018/09/07 jQuery
Vue press 支持图片放大功能的实例代码
2018/11/09 Javascript
利用es6 new.target来对模拟抽象类的方法
2019/05/10 Javascript
微信小程序云函数使用mysql数据库过程详解
2019/08/07 Javascript
JS实现随机抽选获奖者
2019/11/07 Javascript
JavaScript的变量声明与声明提前用法实例分析
2019/11/26 Javascript
vue组件开发之tab切换组件使用详解
2020/08/21 Javascript
Python pycharm 同时加载多个项目的方法
2019/01/17 Python
Linux上使用Python统计每天的键盘输入次数
2019/04/17 Python
详解用python -m http.server搭一个简易的本地局域网
2020/09/24 Python
NICKIS.com荷兰:设计师儿童时装
2020/01/08 全球购物
应届生财务会计求职信
2013/11/05 职场文书
大学校运会广播稿
2014/02/03 职场文书
网络编辑岗位职责
2014/03/18 职场文书
高中生第一学年自我鉴定2015
2014/09/28 职场文书
承诺保证书格式
2015/02/28 职场文书
2015年小学美术工作总结
2015/05/25 职场文书
天鹅湖观后感
2015/06/09 职场文书
基于go interface{}==nil 的几种坑及原理分析
2021/04/24 Golang
如何在CSS中绘制曲线图形及展示动画
2021/05/24 HTML / CSS
Python Matplotlib绘制条形图的全过程
2021/10/24 Python
JavaScript获取URL参数的方法分享
2022/04/07 Javascript