搜索引擎工具
graph TB A((Lucene)) A --> B[Solr] A --> C[ElasticSearch] A --> H[Java] B --> D[RESTful & Admin] B --> E[Core & Field] B --> F[IKAnalyzer] C --> F C --> G[Kibana][TOC]
Lucene
Lucene ([‘lu:si:n]
) 是基于 java 的开源全文索引工具包
本文内容源自 how2j
示例代码:
// 1. 准备中文分词器 IKAnalyzer analyzer = new IKAnalyzer(); // 2. 使用测试数据创建索引 List<String> productNames = new ArrayList<>(); productNames.add("飞利浦led灯泡e27螺口暖白球泡灯家用照明超亮节能灯泡转色温灯泡"); productNames.add("飞利浦led灯泡e14螺口蜡烛灯泡3W尖泡拉尾节能灯泡暖黄光源Lamp"); productNames.add("雷士照明 LED灯泡 e27大螺口节能灯3W球泡灯 Lamp led节能灯泡"); productNames.add("飞利浦 led灯泡 e27螺口家用3w暖白球泡灯节能灯5W灯泡LED单灯7w"); productNames.add("飞利浦led小球泡e14螺口4.5w透明款led节能灯泡照明光源lamp单灯"); productNames.add("飞利浦蒲公英护眼台灯工作学习阅读节能灯具30508带光源"); productNames.add("欧普照明led灯泡蜡烛节能灯泡e14螺口球泡灯超亮照明单灯光源"); productNames.add("欧普照明led灯泡节能灯泡超亮光源e14e27螺旋螺口小球泡暖黄家用"); productNames.add("聚欧普照明led灯泡节能灯泡e27螺口球泡家用led照明单灯超亮光源"); // Directory index = createIndex(analyzer, productNames); Directory index = new RAMDirectory(); IndexWriterConfig config = new IndexWriterConfig(analyzer); IndexWriter writer = new IndexWriter(index, config); for (String name : productNames) { Document doc = new Document(); doc.add(new TextField("name", name, Field.Store.YES)); writer.addDocument(doc); } writer.close(); // 3. 查询器 String keyword = "护眼带光源"; Query query = new QueryParser("name", analyzer).parse(keyword); // 4. 搜索 IndexReader reader = DirectoryReader.open(index); IndexSearcher searcher = new IndexSearcher(reader); int numberPerPage = 1000; System.out.printf("当前一共有%d条数据%n",productNames.size()); System.out.printf("查询关键字是:\"%s\"%n",keyword); System.out.printf("查询字符串分词结果:\"%s\"%n",query); ScoreDoc[] hits = searcher.search(query, numberPerPage).scoreDocs; // 5. 显示查询结果 for (int i = 0; i < hits.length; ++i) { ScoreDoc scoreDoc= hits[i]; int docId = scoreDoc.doc; Document d = searcher.doc(docId); List<IndexableField> fields = d.getFields(); System.out.print((i + 1)); System.out.print("\t" + scoreDoc.score); for (IndexableField f : fields) { System.out.print("\t" + d.get(f.name())); } System.out.println(); } // 6. 关闭查询 reader.close();
执行结果 1:
查询关键字是:"护眼带光源" 查询字符串分词结果:"name:护眼 name:带 name:光源" 1 5.159822 飞利浦蒲公英护眼台灯工作学习阅读节能灯具30508带光源 2 0.43331528 欧普照明led灯泡蜡烛节能灯泡e14螺口球泡灯超亮照明单灯光源 3 0.425806 飞利浦led灯泡e14螺口蜡烛灯泡3W尖泡拉尾节能灯泡暖黄光源Lamp 4 0.425806 飞利浦led小球泡e14螺口4.5w透明款led节能灯泡照明光源lamp单灯 5 0.425806 欧普照明led灯泡节能灯泡超亮光源e14e27螺旋螺口小球泡暖黄家用 6 0.425806 聚欧普照明led灯泡节能灯泡e27螺口球泡家用led照明单灯超亮光源
执行结果 2:
查询关键字是:"led 黄色" 查询字符串分词结果:"name:led name:黄色" 1 0.22168216 飞利浦led小球泡e14螺口4.5w透明款led节能灯泡照明光源lamp单灯 2 0.22168216 聚欧普照明led灯泡节能灯泡e27螺口球泡家用led照明单灯超亮光源 3 0.21906272 雷士照明 LED灯泡 e27大螺口节能灯3W球泡灯 Lamp led节能灯泡 4 0.20684227 飞利浦 led灯泡 e27螺口家用3w暖白球泡灯节能灯5W灯泡LED单灯7w 5 0.1634743 飞利浦led灯泡e27螺口暖白球泡灯家用照明超亮节能灯泡转色温灯泡 6 0.1634743 欧普照明led灯泡蜡烛节能灯泡e14螺口球泡灯超亮照明单灯光源 7 0.16064131 飞利浦led灯泡e14螺口蜡烛灯泡3W尖泡拉尾节能灯泡暖黄光源Lamp 8 0.16064131 欧普照明led灯泡节能灯泡超亮光源e14e27螺旋螺口小球泡暖黄家用
执行结果 3:
查询关键字是:"led 黄" 查询字符串分词结果:"name:led name:黄" 1 2.0358434 欧普照明led灯泡节能灯泡超亮光源e14e27螺旋螺口小球泡暖黄家用 2 0.22168216 飞利浦led小球泡e14螺口4.5w透明款led节能灯泡照明光源lamp单灯 3 0.22168216 聚欧普照明led灯泡节能灯泡e27螺口球泡家用led照明单灯超亮光源 4 0.21906272 雷士照明 LED灯泡 e27大螺口节能灯3W球泡灯 Lamp led节能灯泡 5 0.20684227 飞利浦 led灯泡 e27螺口家用3w暖白球泡灯节能灯5W灯泡LED单灯7w 6 0.1634743 飞利浦led灯泡e27螺口暖白球泡灯家用照明超亮节能灯泡转色温灯泡 7 0.1634743 欧普照明led灯泡蜡烛节能灯泡e14螺口球泡灯超亮照明单灯光源 8 0.16064131 飞利浦led灯泡e14螺口蜡烛灯泡3W尖泡拉尾节能灯泡暖黄光源Lamp
仔细查看执行结果 2 和 3,这两次搜索意图其实很相近,但 Lucene 却返回了完全不同的结果。实际的搜索引擎会考虑用户的搜索意图,例如自动修改用户查询字符串以获得语义(意图)相似的查询字符串然后进行查询,最后向用户展示综合后的查询结果
Solr
Solr ([‘s?ul?]
)是一个开源搜索平台,用于构建搜索应用程序。它建立在 Lucene (全文搜索引擎)之上
Solr 提供了类似 RESTful-API 的方式以便于其他系统与 Solr 进行通信,同时 Solr 提供了 web Admin 界面,便于用户操作与管理
IKAnalyzer
默认的 Solr 安装包不包含中文分词器,此时 Solr 会将中文语句、段落或者文章分解为一个个单字,无法实现中文词语检索。IKAnalyzer 是一个三方中文分词器
以 “研究生命科学” 为例,使用默认的 Solr 分词器,分词结果为 6 个独立的汉字:
研 | 究 | 生 | 命 | 科 | 学
使用 IKAnalyzer 作为分词器,分词结果为 5 个汉语单词:
研究生 | 研究 | 生命科学 | 生命 | 科学
概念
Core
如果说 Solr 相当于一个数据库的话,那么 Core 就相当于一张表
Field,查询时需要指定字段名
Core 相当于表,接下来就要为这个表设置字段,用于存放数据。使用 Solr 进行查询时需要指明查找的字段与查询的词,例如:
SolrUtil.query("name:小米 电视 平板",0,10)
、SolrUtil.query("category:家电",0,10)
常用命令(windows)
- solr.cmd start
- solr.cmd stop -all
- solr.cmd create -c how2java -p 8983,创建 core
- solr.cmd delete -c core1
ElasticSearch
和 Solr 一样, ElasticSearch 基于 Lucene,提供了更为便利的访问和调用
ES 和 Solr 一样没有默认的中文分词器,需要三方工具,安装命令:
elasticsearch-plugin.bat install file:.\elasticsearch-analysis-ik-6.2.2.zip
Kibana
Kibana 是一个开源的分析和可视化平台,设计用于和 Elasticsearch 一起工作。Kibana 是分析 ES 中数据的工具,Kibana 提供了 Dev tools 工具,便于用户使用 RESTful 风格方式向 ES 服务发送请求
默认访问端口:127.0.0.1:5601
索引
索引相当于就是一个数据库服务器上的某个数据库,所以索引也可以看成是 Elastic Search 里的某个数据库
使用 RESTful 风格操控 ES
PUT /how2java?pretty ,添加索引 GET /_cat/indices?v ,查询 DELETE /how2java?pretty , 删除 // 向 product 中插入一条数据 PUT /how2java/product/1?pretty { "name": "蜡烛" }