如何实现全文检索功能之搜索之路

栏目: 后端 · 发布时间: 5年前

内容简介:时间回到20年前。张大胖学校的图书馆网站上线了,张大胖去浏览了一番,发现竟然没有按照关键字搜索图书的功能,大为吃惊之余,又隐约觉得机会来了: 我刚学完Web开发,其中也有数据库相关的知识,也许我可以实现这个功能啊!想到此处,张大胖赶紧查找联系方式,抱着试试看的态度给图书馆的管理员发了一封电子邮件,表达了能实现这个搜索功能的信心和决心。

引子

时间回到20年前。

张大胖学校的图书馆网站上线了,张大胖去浏览了一番,发现竟然没有按照关键字搜索图书的功能,大为吃惊之余,又隐约觉得机会来了: 我刚学完Web开发,其中也有数据库相关的知识,也许我可以实现这个功能啊!

想到此处,张大胖赶紧查找联系方式,抱着试试看的态度给图书馆的管理员发了一封电子邮件,表达了能实现这个搜索功能的信心和决心。

如何实现全文检索功能之搜索之路

没想到真的收到回信了,管理员王老师让他在周四的下午2点半到图书馆3楼307聊一聊。

周四下午,张大胖沐浴更衣以后,如约而至。 经过一番寒暄和介绍,王老师正式进入主题:你打算怎么实现这个全文检索功能啊?

张大胖说:“我可以用 SQL 的 Like来实现。”

王老师笑了:“数据量小的时候Like还凑合,数据量一大,效率就非常低了。”

张大胖有点蒙:“那怎么办?”

王老师说:“得用inverted index才行。”

张大胖知道什么是index, 但是从来没有听说过inverted index,这是什么鬼?

王老师看到他迷茫的脸色,就知道这小子虽然勇气可嘉,但是技术还是有所欠缺,鼓励到:“这样吧,你回去研究研究inverted index, 然后再来实现这个全文检索功能。”

Inverted Index

张大胖灰溜溜地回到宿舍,赶紧拨号上网去查这个inverted index。

张大胖发现有很多人把他翻译成倒排索引,听起来虽然有点古怪,但实际上是一个非常简单的概念。 比如说有两篇文档:

文档1的内容:A computer is a device that can execute operations

文档2的内容:Early computers are big devices

把这两篇文章中的单词都抽取出来,并且记录下这些单词出现在哪个文档中,这就形成了一个简单粗糙的倒排索引。

如何实现全文检索功能之搜索之路

通过这个“倒排索引”,只要给出一个单词,就可以迅速地定位到它在哪个文档中。 用来做全文搜素非常合适。

但是上面的倒排索引有点“粗糙”,还可以在“精化”一下。

1. 对于 a, is , to ,that ,can ,the,are 这些词对搜索来说没什么意义,用户几乎不会用他们搜索,可以过滤掉。

2.  用户搜索的时候虽然输入了computer,但是也希望搜出computers出来,所以需要把复数单词,过去式单词等做还原。

3. 用户虽然输入了device , 但是也希望搜索出Device出来,所以需要把大写都改成小写。

经过这番转换,文档1和文档2的关键字变成了这样:

文档1:[computer] [device] [execute] [operation]

文档2:[early] [computer] [big] [device]

相应地,倒排索引变成了这样:

如何实现全文检索功能之搜索之路

当用户想搜索device 的时候,我们就可以告诉它,在文档1和文档2中都有。

为了更好的统计和高亮显示搜索结果,还可以记录关键词在文章中出现的次数和位置(例如:是第几个单词)

如何实现全文检索功能之搜索之路

架构

明白了inverted index是怎么回事儿, 张大胖觉得只要把那些书籍的标题,介绍,作者等信息给提取出来,形成inverted index,不就可以做关键字检索了吗?

可是转眼一想,这个需求应该是个通用的需求,不仅是图书馆有,很多互联网应用,例如网上商城也需要, 我完全可以设计一个类库出来,让大家去使用啊。

张大胖迅速画出一个架构图出来:

如何实现全文检索功能之搜索之路

看看,不管你是什么类型的文档,HTML, PDF, Word,甚至是数据库的数据,只要能从中抽取出文本,就可以当作我的数据源,对文本做了分析以后,就可以存入索引库。

用户可以发出各种查询,不仅仅是单个关键字,还支持关键字的组合: keyword1 AND keyword2等,对索引库进行搜索以后,把结果返回给用户。

“中间用虚线框起来的部分就是我应该实现的类库!” 张大胖对这个架构很满意。

抽象

接下来就要考虑这个类库对外提供的API了,这是个很烦人的事情。 张大胖的脑海中不由地想起来好基友Bill的谆谆教导:“软件设计就是一个不断抽象的过程。”, 关键是要抽象啊!

可是这个系统似乎有点复杂,张大胖绞尽脑汁想了两天也没有头绪,对于一个刚学会Web开发的同学,立刻就要设计类库,确实是有点勉为其难。

没办法,张大胖只好致电Bill前来帮忙。

Bill对张大胖的痛苦表示了亲切的慰问, 又对架构图表示了适度的赞赏。 他说: “既然有HTML,PDF, Word文档, 很自然,你可以做一个Document的抽象!”

“好像不行吧? 如果数据源是数据库,怎么变成Document? ”

“很简单, 比如一行数据就可以映射到一个Document。 当然,这个转化必须得有 程序员 来完成。程序员决定什么东西是Document。” Bill说。

“Document中有什么东西? ”

“嗯,Document可以有很多属性,每个属性都有名称和值, 我可以把属性叫做Field。比如一个HTML文档,可能有path, title,content等多个Field,其中path可以唯一地标志这个文档, title和content需要做进行分词,形成倒排索引,让用户搜索。” Bill回答。

如何实现全文检索功能之搜索之路

(一个包含多个Field的Document)

“用户创建了Document和Field以后,就可以进行分析了原始的内容划分成一个个Term,” 张大胖开始开窍,“这样,我可以定义一个Analyzer的抽象类,让别的程序可以扩展它。”

“对,分析的结果可以加入索引库,这个操作可以让一个单独的类,比如IndexWriter类来完成。” Bill 说。

“可是IndexWriter如何知道索引应该存在什么地方? 内存? 文件系统?”

“那就再来一个抽象的概念:Directory,表示索引文件的存储。”

张大胖怕忘记,赶紧画类图:

如何实现全文检索功能之搜索之路

“看起来还是挺漂亮的嘛!” 张大胖说。

“好的设计一般都比较漂亮。” Bill 来了一句至理名言。

“对于对于用户搜索来说,肯定得有个叫做Query的东西,用来表达用户的搜索要求。当然,这个Query也应该允许扩展。 ” 张大胖尝试着抽象。

如何实现全文检索功能之搜索之路

“但是这些类使用起来还是比较麻烦, 最好是支持用户输入字符串来表达搜索的意图:(computer or phone) and price”  Bill还是经验老道,“必须得有个解析器来完成从字符串到Query的转化,然后我们让IndexSearcher 来接收Query,就可以实现搜索的功能了。 ”

如何实现全文检索功能之搜索之路

张大胖很兴奋,一个复杂的系统,就这么被搞定了,虽然其中有很多细节没有覆盖,但大的方向已经确定, 细节在具体的开发中来处理吧。

他摩拳擦掌,准备大干一场,把这个设计给实现了。

可是Bill在网上搜索了一会儿,泼了一盆冷水:“大胖,好像有个叫做Lucene的开源系统,和我们的设计很像啊,功能更加强大,要不你就用它这个实现吧。”

张大胖赶紧跑到电脑前去看,果然,这个叫Lucene的家伙实现得非常完善,还有很多高级的功能,比如仅仅是“相似度”这个功能,非得对搜索有深入研究才行,自己是望尘莫及。

他叹了一口气说:“好吧,我去图书馆找王老师,就用这个Lucene吧!”

三年以后

张大胖已经变成了利用Lucene做搜索的高手,各种细节和最佳实践尽在掌握。随着互联网应用的爆炸式增长,搜索变成了一个常见的需求,他甚至在业余时间专门去给人做Lucene的咨询,赚了不少外快。

但是做得多了,张大胖也觉得很烦,这个Lucene用起来实在是太“低级”,很多人向他抱怨: 我就想搜索一下我的商品描述,现在还得理解什么“Directory”,"Analyzer","Query",实在是太复杂了! 还有我们的数据越来越多,索引也越来占的空间也越来越大,怎么才能实现分布式的存储啊?

这样的抱怨听多了,张大胖心想:是时候对Lucene做一层封装,提供一个简单的API了......

后记:接下来还可以讲一下Elastic Search ,也不知道大家是否感兴趣,再加上这篇文章已经很长了,就停笔了。 如果各位感兴趣的,留言告诉我一下,我会继续写下去。

如何实现全文检索功能之搜索之路

【本文为51CTO专栏作者“刘欣”的原创稿件,转载请通过作者微信公众号coderising获取授权】

戳这里,看该作者更多好文


以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

PHP&MySQL Web数据库应用开发指南

PHP&MySQL Web数据库应用开发指南

Hugb E. Williams、David Lane / 谢君英 / 中国电力出版社 / 2003-5 / 69.00元

一起来看看 《PHP&MySQL Web数据库应用开发指南》 这本书的介绍吧!

CSS 压缩/解压工具
CSS 压缩/解压工具

在线压缩/解压 CSS 代码

XML 在线格式化
XML 在线格式化

在线 XML 格式化压缩工具

HEX HSV 转换工具
HEX HSV 转换工具

HEX HSV 互换工具