登陆注册
19122000000029

第29章 MySQL的全文搜索(3)

程序运行,在搜索栏中输入词语“princess”,单击“搜索”按钮,执行全文搜索,在文本区域中显示结果。”

类似地,在搜索栏中输入“bobby”,单击“搜索”按钮。

6.3.2Web应用

使用PHP开发一个Web应用程序,连接MySQL数据库,执行全文搜索。这个案例只作为演示。

只含有一个文件mysql.php,代码如下:

mysql.php

<form action=mysql.php method=post>

<input name=search><input type=submit value="search"name="submit">

</form>

<?php

if(isset($ POST["submit"]))

{

echo"<table border=2bordercolor=red>";

$ connect=@ mysql connect("localhost","root","tianen");//连接数据库服务器

if(!$ connect)//验证连接是否成功

{

echo"wrong.";

exit;

}

mysql select db("tianen",$ connect);//选择数据库

$ query="select*from en where match(title,body)against("".$ POST["search"]."")";

//构造sql选择语句

$ result=mysql query($ query);//执行sql语句,将结果赋予$ result

$ rows=@ mysql num rows($ result);//返回记录数目

for($ i=0;$ i<$ rows;$ i++)//遍历记录

{

@ mysql data seek($ result,$ i);//定位记录

$ data=@ mysql fetch array($ result);//获得记录数组$ data

$ id=$ data[0];//获得相应字段值

$ title=$ data[1];

$ body=$ data[2];

echo"<tr><td>".$ id."</td><td>".$ title."</td><td>".$ body."</td>

</tr>";

}

echo"</table>";

mysql free result($ result);

mysql close($ connect);//关闭数据库连接

}

?>

在搜索栏中输入词语“princess”,单击“搜索”按钮,执行全文搜索,在网页上显示结果。

6.4中文问题

在英文排版时,词语间是以空格区分的,所以英文的分词是基于空格的。但是涉及中文等文字就没有这么简单了,因为中文词间并没有明显的区隔,所以中文的分词则是按照字典、词库的匹配和词的频度统计,或是基于句法、语法分析的分词,而MySQL并不具备此功能,所以MySQL对中文全文检索的支持几乎为零。

然而,中国也有很多使用MySQL的应用程序,许多程序都需要全文搜索的支持,该怎么办呢?

想了一下,可以进行编码。把汉字编成英文字符,字与字之间加上空格,然后MySQL就会识别这些字符了,并对其进行分词。

6.4.1编码解决

把汉字编成英文字符,这是什么意思?汉字怎么能变成英文字符?

1.拼音编码

可以看这个例子,“我爱祖国”,把其中的每个字变成拼音,中间再加上空格,然后得到的结果就是“wo ai zu guo”,在这种情况下,MySQL会把“wo”,“ai”等都当成英文单词。我们希望输入“祖国”,能和“我爱祖国”进行对比,但做不到。所以,用拼音作为桥梁,输入“zu guo”,然后和“wo ai zu guo”进行对比,还是可以找到一些结果的。

这就是网上某人的发明,写一个拼音转换程序,可以得到汉字的拼音表示,然后实现拼音和拼音之间的对比。

举个例子,现在数据库中有两条记录:“我爱计算机”和“努力学习”。

搜索的词是“学习”

这个时候,程序把“学习”变成“xue xi”,把数据库的两条记录变成:“wo ai ji suan ji”和“nuli xue xi”。

然后执行MySQL的全文搜索,当然,可以搜到结果。

这个方法有很多弊端。

它需要修改MySQL被编入索引单词的最小长度,把4改成2,因为汉字的拼音都是很短的。

需要编写一个程序实现数据库内信息的自动拼音转换,以及把原汉字文档保留副本等。

当然,这个程序并不难写。

输入“奴隶”,会查到“努力”,即便可以标出声调,比如“奴隶”是“nu2li4”,“努力”是“nu3li4”,但还是会有很多问题,汉语中同音不同意的词太多了。

不管怎样,它可以作为一种折中的方案,至少可以搜出一点东西来,不致于看着数据傻眼。

类似的方案有无数种,拼音只是编码方式的一种,而且是不怎么样的一种,有多少种编码方式就有多少种折中方案。

这里举一个例子,来说明通过汉字编码方式来解决中文全文搜索问题。

首先,在tianen数据库中建立一个新表格,语句如下:

CREATE TABLE ZH

id INTAUTO INCREMENT NOT NULL PRIMARY KEY,

title VARCHAR(200),

body TEXT,

new TEXT,

FULLTEXT(new),

FULLTEXT(body)

)type=MyISAM;

title是标题,body是汉字内容,new是编码后存储到数据库中的内容。对body和new分别作了全文索引。

向表格中添加若干测试数据,语句如下:

INSERT INTO ZH(title,body,new)VALUES("祖国","我爱祖国","wo ai zu guo");

INSERT INTO ZH(title,body,new)VALUES("人民","我爱人民","wo ai ren min");

INSERT INTO ZH(title,body,new)VALUES("山川","我爱山川","wo ai shan chuan");

现在,执行全文搜索,语句如下:

select*from zh where match(new)against("shan chuan");

select*from zh where match(new)against("zu guo");

可以看出来,“shan chuan”可以搜索出结果,这说明MySQL已经把它按照英文去处理了。

但“zu guo”无法搜索出结果,这是因为它们的长度都不到4,没有被键入索引。

依据这个原理去开发数据库程序,可以在数据库中新增一列,专门存储汉字搜索列的拼音拆分结果,这样,就可以搜索出一些结果来,虽然不准确,但还是可以凑合用。

2.汉字内码

在拼音编码方案里有一个问题,就是不同的汉字编码之后结果会相同,如“花”,“华”。由此导致的搜索不准确是可以避免的,因为汉字各不相同,把它们按照某种算法加密之后,应该也可以让它们的加密结果各不相同。这种加密算法是非常多的。MD5曾经是用得最广泛的算法,但是后来已经证明,不同的字符串经过MD5加密之后能得到相同的值,因此MD5不再是理想的单项加密算法了。SHA1算法目前被证明是非常好的加密算法,不妨尝试一下。

计算机上使用的汉字有两类代码,一类称为外码,用来输入汉字,如拼音码、郑码、五笔字型码等。由于人们不断寻求更佳的汉字输入法,因此外码也就层出不穷。不同的外码规则也不同,如果计算机内部存储汉字时,也采用这些五花八门的编码,势必使汉字系统过于复杂。

因此,不论用什么输入法输入的汉字,在存入存储器时,都将它的外码转换成一种统一的代码,这就是汉字内码。

一个汉字的内码由两个字节组成。汉字内码与区位码之间有一个简单的关系:

内码第一字节=区码+160

内码第二字节=位码+160

比如,查区位码表知道,“啊”字在16区01位,它的内码为:

第一字节=16+160=176

第二字节=1+160=161

英文字符的代码ASCII只用一个字节表示。为什么一个汉字要用两个字节来表示呢?

这是因为一个字节(8位二进制数)能表示的最大整数范围是0~255,也就是说最多能表示256种不同的状态,这用于表示几十个英文字符足够了。但是汉字有成千上万个,所以至少要用两个字节(16位二进制数)来编码。两个字节最多可有65536种不同的编码。

由于大多英文软件只处理单字节对象,而汉字内码又是双字节的,这就会带来一些问题。

比如我们用vi编辑一个文本文件,要删掉其中的一个汉字时,要敲两次删除键才能删掉。若是只删了一下,后面的汉字就变得面目全非了。道理很简单:删一下,只删掉了汉字内码的一个字节,剩下的一个字节和下一个汉字的头一个节就构成了另一个汉字或符号的内码,于是就显示出和这个内码对应的汉字或符号。依次错位,后面的汉字就全变了。

在PHP里面,ord()函数可以获得字符的内码第一字节,下面的案例,使用了sha1和ord两个函数来编码字符。

案例名称:编码中文

程序名称:zh.php

<?php

echo ord("我")."<br>";

echo ord("爱")."<br>";

echo ord("山")."<br>";

echo ord("川")."<br>";

echo"<hr>";

echo sha1("我")."<br>";

echo sha1("爱")."<br>";

echo sha1("山")."<br>";

echo sha1("川")."<br>";

?>

比较一下,不难看出SHA1算法生成的字符串太长,而ORD算法比较适合于编码中文,优于拼音编码。

6.4.2建议和提示

除了这种编码方法之外,还有其他的一些中文编码方法。

要注意,只有MyISAM类型的表才支持全文搜索,所以建立表格时应该标示出“type=MyISAM”。

CREATE TABLE EN

id INTAUTO INCREMENT NOT NULL PRIMARY KEY,

title VARCHAR(200),

body TEXT,

FULLTEXT(title,body)

)type=MyISAM;

如果一个表原本不是MyISAM类型的,要将其修改为MyISAM类型,可以使用下面的语句:

alter table EN type=MyISAM;

为一个表增加全文索引的方法如下:

alter table EN add fulltext(title);

小结

本章介绍了MySQL全文搜索的原理和使用方法。并且探讨了解决中文搜索的方案。需要重点掌握的是MySQL进行全文搜索的格式。

思考与练习

1.MySQL数据库有哪些优良特性?

2.使用PHP和MySQL开发一套全文搜索系统。

同类推荐
  • 安全教育高一(上)

    安全教育高一(上)

    《安全教育》系列编写的是孩子安全教育的图书。本书主要讲述的是自我保护能力是孩子们快乐健康成长的必备能力。只有学会自我保护,远离危险,我们的孩子才能拥有幸福,享受美好的生活。
  • 没有年代的故事

    没有年代的故事

    《没有年代的故事》作者刘建超是我国小小说界具有阳刚气的作家,读他的作品令人产生强烈的震撼。其作品大多正气逼人,富于理想主义色彩。从外在形态上看,刘建超的作品立意与人物内涵也许最接近于所谓主流意识形态,但细细琢磨起来,你会体察到,内在地支撑着他的创作理念,是对崇高信念与理想人格的推崇和呼唤。换言之,他是站在平民的立场上,痛切地针对当代社会的某些精神缺失有感而发的。他笔下的伟人、将军或平民英雄决非虚无缥缈、高不可攀,其人其事都是在我们的生活中曾经发生过或者可能发生的。
  • 语文新课标课外必读第十辑——飞行村

    语文新课标课外必读第十辑——飞行村

    国家教育部颁布了最新《语文课程标准》,统称新课标,对中、小学语文教学指定了阅读书目,对阅读的数量、内容、质量以及速度都提出了明确的要求,这对于提高学生的阅读能力,培养语文素养,陶冶情操,促进学生终身学习和终身可持续发展,对于提高广大人民的文学素养具有极大的意义。
  • 中学化学课程资源丛书-化学之声

    中学化学课程资源丛书-化学之声

    作为科学教育的重要组成部分,新的化学课程倡导从学生素质的培养和社会发展的需要出发,发挥学科自身的优势,将科学探究作为课程改革的突破口,激发学生的主动性和创新意识,促使学生积极主动地去学习,使获得化学知识和技能的过程也成为理解化学、进行科学探究、联系社会生活实际和形成科学价值观的过程。本套丛书集知识性与实用性于一体,是学生在学习化学知识及教师在进行引导的过程中不可或缺的一套实用工具书。
  • 汽车文化

    汽车文化

    本书是一本集知识性与趣味性于一体的汽车基础知识和汽车文化教材,为职业学校学生学习汽车基础知识,感受、传播和弘扬汽车文化提供了一个很好的平台,可作为职业教育学生的公共选修课教材。本书讲述了汽车史话、汽车魅力、汽车博览、汽车风姿、汽车会友、汽车改装、汽车赛事、汽车展望及汽车服务人才等知识。通过对本书的学习,能拓宽学生的知识面,培养学生对汽车的兴趣,更全面的了解专业、热爱专业。本教材内容丰富、图文并茂,合于职业教育院校汽车相关专业及培训班的师生使用,也适合于汽车维修技术人员、驾驶员以及汽车爱好者参考阅读.
热门推荐
  • 帝国瑰色

    帝国瑰色

    本书通过一段段发生在中国古代的情感故事,揭示帝国宫廷深处的政治秘密和感情谜团,诠释中国皇权制度下的爱恨情仇,走出帝王将相崇拜的迷津。
  • 越史略

    越史略

    本书为公版书,为不受著作权法限制的作家、艺术家及其它人士发布的作品,供广大读者阅读交流。
  • 爱你的另一个人

    爱你的另一个人

    作为非亲生的兄妹,贾南对叶茗的单恋,终究没有好结果。
  • 启真1

    启真1

    《启真(1人文主义)》包括:专题、书评、序与跋、书摘、品书、书荐六部分,收录了:《人文主义者论教育》《人口与社会——读马尔萨斯<人口原理>》、《文字与心史——解读乡绅刘大鹏及其<退想斋日记>》、《理解休谟经济思想的三个维度》、《西南联大的学风》、《法藏的譬喻:因袭故典还是自出机杼?》、《“黄跋”的魅力》、《欲望之书》等论文。
  • 纵横异界之绝杀

    纵横异界之绝杀

    离奇遭遇至他遁入异界,神秘身世却助他步步为营。一个少年无意解开封印,被迫去完成一个不可能完成的任务!神秘的身世,纷乱的大陆手到擒来的把妹技巧酣畅淋漓的热血打斗!看他一介凡人如何揭穿惊天阴谋,在异界的残酷厮杀之中横扫双界,傲视群雄!醉卧美人膝,笑看风云起。败,不能输掉信念;死,不能丢掉尊严!看萧风如何翻手为云覆手为雨,屠遍天下不义人!
  • 神魂变

    神魂变

    一个世人眼中的废物,家族抛弃的子弟,入墓救生,却偶得神魂,机缘巧合的相逢,让他踏上了一条自己也没有方向的路……
  • 兔子与窝边草的pk:鬼妖大驾到

    兔子与窝边草的pk:鬼妖大驾到

    曾经,他冰冷无情,她便费尽心思地靠近。当他终于放下戒备,对她全情相待之时,她却碎他内丹、毁他妖身,为此甚至不惜与他同归于尽。他侥幸存下一魄,苦修至今,终于得到一副灵体找到她,她却早已经再世为人,忘记了一切。不过没关系,他有的是时间和耐心让她记起来。这一世,不管是为了复仇,还是为了拿回内丹,他都绝不会再放过她……这既是一个兔子与窝边草pk的故事,同时也是一个复仇鬼妖成功晋级为忠犬男票的另类爱情故事。~~~(≧?≦)ゞ喜欢就收藏一下吧,求关注,求点击,求收藏,求各种,各种求……
  • 拾起记忆

    拾起记忆

    剧情的话纠结好久准备写校园悬疑~不惊悚还很甜各位看官请放心!另:处女作思密达大家多支持!评论收藏,推荐小票~~都来!!
  • 此曲上邪

    此曲上邪

    启圣三年文惠皇后崩,留下幼女。皇城暗流涌动,御马失控,他救她水火。入宫为师,上邪轻咏。他笑她如花美眷轻许流年,她启唇似咏上邪,说的却是我愿与君长诀。十里桃花,为谁远嫁?看她红衣上马,残阳烙心上朱砂。
  • TFBOYS之你是不一样的风景

    TFBOYS之你是不一样的风景

    曾经的他们已是过去,现在的他们能否守护住他们的爱情?也许愈是刻骨铭心的爱情愈是脆弱,就像盛夏的泡沫……伟大的是爱情,强悍的是命运,他们能否逃过命运的捉弄?他是她眼中最美好的风景,而她是他一生中最珍贵而不一样的风景……