mysql中文全文索引
MySQL在高并发连接、
数据库记录数较多的情况下,SELECT ... WHERE ... LIKE '%...%'的全文搜索方式不仅效率差,而且以通配符%和_开头作查询时,使用不到索引,需要全表扫描,对数据库的压力也很大。MySQL针对这一问题提供了一种全文索引解决方案,这不仅仅提高了性能和效率(因为MySQL对这些字段做了索引来优化搜索),而且实现了更高质量的搜索。但是,至今为止,MySQL对中文全文索引无法正确支持。 www.2cto.com
中文与西方文字如英文的一个重要区别在于,西方文字以单词为单位,单词与单词之间以空格分隔。而中文以字为单位,词由一个或多个字组成,词与词之间没有空格分隔。当试图在一个含有中文字符的字段中使用全文搜索时,不会得到正确的结果,原因在于中文中没有像英文空格那样对词定界,不能以空格作为分割,对中文词语进行索引。
一、MySQL中文全文索引插件
mysqlcft的特点:
1、优点:
①、精准度很高:采用自创的“三字节交叉切分算法”,对中文语句进行分割,无中文分词词库,搜索精准度远比中文分词算法高,能达到LIKE '%...%"的准确率。
②、查询速度快:查询速度比LIKE '%...%"搜索快3~50倍,文章末尾有测试结果;
③、标准插件式:以MySQL 5.1全文索引的标准插件形式开发,不修改MySQL源代码,不影响MySQL的其他功能,可快速跟进MySQL新版本;
④、支持版本多:支持所有的MySQL 5.1 Release Candidate版本,即MySQL 5.1.22 RC~最新的MySQL 5.1.25 RC;
⑤、支持字符集:支持包括GBK、GB2312、UTF-8、Latin1、BIG5在内的MySQL字符集(其他字符集没有测试过);
⑦、适合分布式:非常适合MySQL Slave分布式系统架构,无词库维护成本,不存在词库同步问题。
2、缺点:
①、mysqlcft中文全文索引只适用于MyISAM表,因为MySQL只支持对MyISAM表建立FULLTEXT索引;
②、MySQL不能静态编译安装,否则无法安装mysqlcft插件;
③、基于“三字节交叉切分算法”的索引文件会比海量、ft-hightman等基于“中文分词算法”的索引文件稍大,但不是大很多。根据我的测试,mysqlcft全文索引的.MYI索引文件是.MYD数据文件的2~5倍。
配置文件中添加
[mysqld]
ft_min_word_len = 1
附:MySQL配置文件在全文索引应用中的优化
[mysqld]
# key_buffer 指定用于索引的缓冲区大小,在全文索引中,增加它可得到更好的索引处理与查询性能
key_buffer = 512M
# sort_buffer_size 为查询排序时所能使用的缓冲区大小,全文索引的SQL语句之后通常会使用ORDER BY排序,增加它可以加快SQL语句执行时间。该参数对应的分配内存是每连接独占,100个连接使用的内存将是32M*100=3200M
sort_buffer_size = 32M
# 对大于可用内存的表执行GROUP BY或ORDER BY操作,应增加read_rnd_buffer_size的值以加速排序操作后面的行读取
read_rnd_buffer_size = 64M
# 如果表出现故障或索引出错,REPAIR TABLE时用到的缓冲区大小
myisam_sort_buffer_size = 128M
# 确定使用的filesort算法的索引值大小的限值
max_length_for_sort_data = 64
# MySQL全文索引查询所用关键词最小长度限制(不要改变这项值)
ft_min_word_len = 1
# 降低UPDATE优先级,设置查询优先
low_priority_updates = 1
wget http://mysqlcft.googlecode.com/files/mysqlcft-1.0.0-i386-bin.tar.gz
tar zxvf mysqlcft-1.0.0-i386-bin.tar.gz
cp mysqlcft.so /usr/local/mysql1/lib/mysql/plugin/
--安装引擎
INSTALL PLUGIN mysqlcft SONAME 'mysqlcft.so';
--查看是否安装成功 www.2cto.com
SELECT * FROM mysql.plugin;
SHOW PLUGINS;
--创建索引
use test
ALTER IGNORE TABLE pa_gposts ADD FULLTEXT INDEX full_text_title(title) WITH PARSER mysqlcft;
--修复索引
REPAIR TABLE pa_gposts QUICK;
性能比较
没有添加索引之前
SELECT * FROM pa_gposts WHERE MATCH(title) AGAINST ('医院' IN BOOLEAN MODE) limit 0,30;
4 rows in set (1 min 12.69 sec)
这种查询出的结果单词的前后都要有停止字,查询速度还是很慢,因为没有索引
mysql> explain SELECT * FROM pa_gposts WHERE MATCH(title) AGAINST ('医院' IN BOOLEAN MODE) limit 0,30;
+----+-------------+-----------+------+---------------+------+---------+------+--------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-----------+------+---------------+------+---------+------+--------+-------------+
| 1 | SIMPLE | pa_gposts | ALL | NULL | NULL | NULL | NULL | 213193 | Using where |
+----+-------------+-----------+------+---------------+------+---------+------+--------+-------------+
创建索引后
SELECT * FROM pa_gposts WHERE MATCH(title) AGAIN