基于 Mysql 实现一个简易版搜索引擎_Mysql

来源:脚本之家  责任编辑:小易  
目录
基于 Mysql 实现一个搜索引擎一、ngram 全文解析器二、创建全文索引1、建表时创建全文索引2、通过 alter table 方式3、通过 create index 方式三、检索方式1、自然语言检索(NATURAL LANGUAGE MODE)四、与 Like 对比

基于 Mysql 实现一个搜索引擎

前言:

其实 Mysql 很早就支持全文索引了,只不过一直只支持英文的检索,从5.7.6 版本开始,Mysql 就内置了 ngram 全文解析器,用来支持中文、日文、韩文分词。

Mysql 全文索引采用的是倒排索引的原理,在倒排索引中关键词是主键,每个关键词都对应着一系列文件,这些文件中都出现了这个关键词。这样当用户搜索某个关键词时,排序程序在倒排索引中定位到这个关键词,就可以马上找出所有包含这个关键词的文件。

本文测试,基于 Mysql 8.0 版本,数据库引擎采用的是 InnoDB

一、ngram 全文解析器

ngram 就是一段文字里面连续的 n 个字的序列。ngram 全文解析器能够对文本进行分词,每个单词是连续的 n 个字的序列。例如,用 ngram 全文解析器对“你好靓仔”进行分词:

n=1: '你', '好', '靓', '仔' 
n=2: '你好', '好靓', '靓仔' 
n=3: '你好靓', '好靓仔' 
n=4: '你好靓仔'

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

可以通过以下命令查看 Mysql 默认的 ngram_token_size 大小:

show variables like 'ngram_token_size'

有两种方式可以设置全局变量 ngram_token_size 的值:

(1)启动 mysqld 命令时指定:

mysqld --ngram_token_size=2

(2)修改 Mysql 配置文件 my.ini,末尾增加一行参数:

ngram_token_size=2

二、创建全文索引

1、建表时创建全文索引

CREATE TABLE `article` (
  `id` bigint NOT NULL,
  `url` varchar(1024) COLLATE utf8mb4_general_ci NOT NULL DEFAULT '',
  `title` varchar(256) COLLATE utf8mb4_general_ci NOT NULL DEFAULT '',
  `source` varchar(32) COLLATE utf8mb4_general_ci DEFAULT '',
  `keywords` varchar(32) COLLATE utf8mb4_general_ci DEFAULT NULL,
  `publish_time` timestamp NULL DEFAULT NULL,
  PRIMARY KEY (`id`),
  FULLTEXT KEY `title_index` (`title`) WITH PARSER `ngram`
) 

ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci;

2、通过 alter table 方式

ALTER TABLE article ADD FULLTEXT INDEX title_index(title) WITH PARSER ngram;

3、通过 create index 方式

CREATE FULLTEXT INDEX title_index ON article (title) WITH PARSER ngram;

三、检索方式

1、自然语言检索(NATURAL LANGUAGE MODE)

自然语言模式是 MySQL 默认的全文检索模式。自然语言模式不能使用操作符,不能指定关键词必须出现或者必须不能出现等复杂查询。

示例:

select * from article where MATCH(title) AGAINST ('北京旅游' IN NATURAL LANGUAGE MODE);

// 不指定模式,默认使用自然语言模式
select * from article where MATCH(title) AGAINST ('北京旅游');

可以看出,该模式下根据“北京旅游”搜索,可以搜索出包含“北京”的或者包含“旅游”的内容,因为它是根据自然语言分成了两个关键词。

上面示例中返回的结果会自动按照匹配度排序,匹配度高的在前面,匹配度是一个非负浮点数。

示例:

// 查看匹配度
select * , MATCH(title) AGAINST ('北京旅游') as score from article where MATCH(title) AGAINST ('北京旅游' IN NATURAL LANGUAGE MODE);

2、布尔检索(BOOLEAN MODE)

布尔检索模式可以使用操作符,可以支持指定关键词必须出现或者必须不能出现或者关键词的权重高还是低等复杂查询。

示例:

// 无操作符
// 包含“约会”或“攻略”
select * from article where MATCH(title) AGAINST ('约会 攻略' IN BOOLEAN MODE);

// 使用操作符
// 必须包含“约会”,可包含“攻略”
select * from article where MATCH(title) AGAINST ('+约会 攻略' IN BOOLEAN MODE);

更多操作符示例:

'约会 攻略' 
无操作符,表示或,要么包含“约会”,要么包含“攻略”

'+约会 +攻略'
必须同时包含两个词

'+约会 攻略'
必须包含“约会”,但是如果也包含“攻略”的话,匹配度更高。

'+约会 -攻略'
必须包含“约会”,同时不能包含“攻略”。

'+约会 ~攻略'
必须包含“约会”,但是如果也包含“攻略”的话,匹配度要比不包含“攻略”的记录低。

'+约会 +(>攻略 <技巧)'
查询必须包含“约会”和“攻略”或者“约会”和“技巧”的记录,但是“约会 攻略”的匹配度要比“约会 技巧”高。

'约会*'
查询包含以“约会”开头的记录。

'"约会攻略"'
使用双引号把要搜素的词括起来,效果类似于like '%约会攻略%',
例如“约会攻略初级篇”会被匹配到,而“约会的攻略”就不会被匹配。

四、与 Like 对比

全文索引和 like 查询对比,有以下优点:

like 只是进行模糊匹配,全文索引却提供了一些语法语义的查询功能,会将要查的字符串进行分词操作,这决定于 Mysql 的词库。 全文索引可以自己设置词语的最小、最大长度,要忽略的词,这些都是可以设置的。 用全文索引去某个列查一个字符串,会返回匹配度,可以理解为匹配的关键字个数,是个浮点数。

而且全文检索的性能也是优于 like 查询的

以下是以 50w 左右数据进行的测试:

// like 查询
select * from article where title like '%北京%';

// 全文索引查询
select * from article where MATCH(title) AGAINST ('北京' IN BOOLEAN MODE);

可以看出 like 查询是 1.536s,全文索引查询是 0.094s,快了16倍左右。

全文索引能快速搜索,但是也存在维护索引的开销。字段长度越大,创建的全文索引也越大,会影响DML语句的吞吐量。数据量不大的情况下可以采用全文索引来做搜索,简单方便,但是数据量大的话还是建议用专门的搜索引擎 ElasticSearch 来做这件事。

以上就是基于 Mysql 实现一个简易版搜索引擎的详细内容,更多关于 Mysql 实现搜索引擎的资料请关注真格学网其它相关文章!希望大家以后多多支持真格学网!

您可能感兴趣的文章:Mysql实现简易版搜索引擎的示例代码MySQL全文索引实现简单版搜索引擎实例代码详细介绍基于MySQL的搜索引擎MySQL-Fullltextscrapy+flask+html打造搜索引擎的示例代码python基于搜索引擎实现文章查重功能Python实战之手写一个搜索引擎Python大批量搜索引擎图像爬虫工具详解360搜索引擎自动收录php改写方案php记录搜索引擎爬行记录的实现代码Python无损音乐搜索引擎实现代码

  • 本文相关:
  • mysql索引基数概念与用法示例
  • 监听mysql表内容变化 mysql开启binlog
  • mysql数据库事务隔离级别介绍(transaction isolation level)
  • mysql修改开启允许远程连接的方法
  • win10免安装版本的mysql安装配置教程
  • mysql笔记之数学函数详解
  • mysql使用临时表加速查询的方法
  • mysql数据库开启、关闭、查看函数功能的方法
  • mysql的udf编程之非阻塞超时重传
  • mysql 日期和时间格式转换实现语句
  • 求高人给一个用PHP+MySQL实现的简单的数据库查询功能的P...
  • 求高人给一个用PHP+MySQL实现的简单的数据库查询代码
  • 用MyEclipse+Tomcat+MySQL实现一简单的留言管理系统,谁给...
  • 如何用java 5分钟实现一个最简单的mysql代理服务器
  • PHP+MYSQL实现读写分离简单实战
  • 一个简单的php实现的MySQL数据浏览器
  • php实现Mysql简易操作类
  • 求一个myeclipse+mysql+JSP的新闻发布系统,简单点的,能实现...
  • Ajax PHP JavaScript MySQL实现简易无刷新在线聊天室
  • 用PHP+MYSQL做一个简单的点餐系统的后台,初学者. 请高手指...
  • 使用函数递归实现基于php和MySQL的动态树型菜单
  • 网站首页网页制作脚本下载服务器操作系统网站运营平面设计媒体动画电脑基础硬件教程网络安全mssqlmysqlmariadboracledb2mssql2008mssql2005sqlitepostgresqlmongodbredisaccess数据库文摘数据库其它首页mysqlmysql实现简易版搜索引擎的示例代码mysql全文索引实现简单版搜索引擎实例代码详细介绍基于mysql的搜索引擎mysql-fullltextscrapy+flask+html打造搜索引擎的示例代码python基于搜索引擎实现文章查重功能python实战之手写一个搜索引擎python大批量搜索引擎图像爬虫工具详解360搜索引擎自动收录php改写方案php记录搜索引擎爬行记录的实现代码python无损音乐搜索引擎实现代码mysql索引基数概念与用法示例监听mysql表内容变化 mysql开启binlogmysql数据库事务隔离级别介绍(transaction isolation level)mysql修改开启允许远程连接的方法win10免安装版本的mysql安装配置教程mysql笔记之数学函数详解mysql使用临时表加速查询的方法mysql数据库开启、关闭、查看函数功能的方法mysql的udf编程之非阻塞超时重传mysql 日期和时间格式转换实现语句mysql安装图解 mysql图文安装教程can""""t connect to mysql servwindows下mysql5.6版本安装及配置mysql字符串截取函数substring的mysql创建用户与授权方法mysql提示:the server quit withmysql之timestamp(时间戳)用法mysql——修改root密码的4种方法mysql日期数据类型、时间类型使用mysql update语句的用法详解mysql导入导出sql文件简析mysql采用group_concat合并多条数据显示的浅谈mysql返回boolean类型的几种情况使用bin-log日志还原数据库的例子sql字符串以及数字常用操作汇总解决mysql无法远程连接的方法mysql dba教程:mysql性能优化之缓存参数mysql启动报错mysql server pid file cou浅析mysql 主键使用数字还是uuid查询快mysql主从同步、读写分离配置步骤
    免责声明 - 关于我们 - 联系我们 - 广告联系 - 友情链接 - 帮助中心 - 频道导航
    Copyright © 2017 www.zgxue.com All Rights Reserved