一步一步学lucene——(第二步:示例篇)
在上面的篇幅中我们已经了解到了lucene,及lucene到底是做什么的,什么情况下才能够使用lucene,下面我们就结合一个例子来详细说明一下lucene的API,看看lucene是如何工作的。
lucene的下载
其实这个很简单了,直接到baidu或者google上搜索一下,一般情况下第一个就是我们要的链接。下边给出lucene下载的链接:
图:lucene下载主页面
配置环境
我们下面要做很多的测试,会建立很多的测试工程,如果一个一个手动的添加jar包会非常的麻烦,那么我们就需要配置eclipse环境。
打开eclipse,选择windows->preferences->java->build path->user libraries
将我们上边下载后的lucene中的包全部加载到这个用户变量中。
图:eclipse中加入的用户变量
建立索引
下面这个程序就是读取指定文件夹下的文件并且将文件生成索引的过程,它有两个参数,一个是要索引的文件路径,一个是索引存放的路径。
我们将文件放到我们硬盘的目录上,然后通过程序建立索引。
索引程序如下:
1 public class Indexer {
2
3 public static void main(String[] args) throws Exception {
4 if (args.length != 2) {
5 throw new IllegalArgumentException("Usage: java "
6 + Indexer.class.getName() + " <index dir> <data dir>");
7 }
8 String indexDir = args[0]; // 1
9 String dataDir = args[1]; // 2
10
11 long start = System.currentTimeMillis();
12 Indexer indexer = new Indexer(indexDir);
13 int numIndexed;
14 try {
15 numIndexed = indexer.index(dataDir, new TextFilesFilter());
16 } finally {
17 indexer.close();
18 }
19 long end = System.currentTimeMillis();
20
21 System.out.println("Indexing " + numIndexed + " files took "
22 + (end - start) + " milliseconds");
23 }
24
25 private IndexWriter writer;
26
27 public Indexer(String indexDir) throws IOException {
28 Directory dir = FSDirectory.open(new File(indexDir));
29 writer = new IndexWriter(dir, // 3
30 new StandardAnalyzer( // 3
31 Version.LUCENE_30),// 3
32 true, // 3
33 IndexWriter.MaxFieldLength.UNLIMITED); // 3
34 }
35
36 public void close() throws IOException {
37 writer.close(); // 4
38 }
39
40 public int index(String dataDir, FileFilter filter) throws Exception {
41
42 File[] files = new File(dataDir).listFiles();
43
44 for (File f : files) {
45 if (!f.isDirectory() && !f.isHidden() && f.exists() && f.canRead()
46 && (filter == null || filter.accept(f))) {
47 indexFile(f);
48 }
49 }
50
51 return writer.numDocs(); // 5
52 }
53
54 private static class TextFilesFilter implements FileFilter {
55 public boolean accept(File path) {
56 return path.getName().toLowerCase() // 6
57 .endsWith(".txt"); // 6
58 }
59 }
60
61 protected Document getDocument(File f) throws Exception {
62 Document doc = new Document();
63 doc.add(new Field("contents", new FileReader(f))); // 7
64 doc.add(new Field("filename", f.getName(), // 8
65 Field.Store.YES, Field.Index.NOT_ANALYZED));// 8
66 doc.add(new Field("fullpath", f.getCanonicalPath(), // 9
67 Field.Store.YES, Field.Index.NOT_ANALYZED));// 9
68 return doc;
69 }
70
71 private void indexFile(File f) throws Exception {
72 System.out.println("Indexing " + f.getCanonicalPath());
73 Document doc = getDocument(f);
74 writer.addDocument(doc); // 10
75 }
76
77 }
然后在工程上点击右键Run->Run configuration,新建一个Java Application,输入两个参数一个是索引目录,一个是文件存放目录
图:配置运行界面
运行后可以行到分析结果,当然目录中索引的内容不同得到的结果也就会不同。
图:索引txt文件时输出
根据索引查询
因为这里边还没涉及到中文的部分,所以我们查询所有文档中包括"RUNNING"的文档。
程序内容如下:
1 public class Searcher {
2
3 public static void main(String[] args) throws IllegalArgumentException,
4 IOException, ParseException {
5 if (args.length != 2) {
6 throw new IllegalArgumentException("Usage: java "
7 + Searcher.class.getName() + " <index dir> <query>");
8 }
9
10 String indexDir = args[0]; // 1
11 String q = args[1]; // 2
12
13 search(indexDir, q);
14 }
15
16 public static void search(String indexDir, String q) throws IOException,
17 ParseException {
18
19 Directory dir = FSDirectory.open(new File(indexDir)); // 3
20 IndexSearcher is = new IndexSearcher(dir); // 3
21
22 QueryParser parser = new QueryParser(Version.LUCENE_30, // 4
23 "contents", // 4
24 new StandardAnalyzer( // 4
25 Version.LUCENE_30)); // 4
26 Query query = parser.parse(q); // 4
27 long start = System.currentTimeMillis();
28 TopDocs hits = is.search(query, 10); // 5
29 long end = System.currentTimeMillis();
30
31 System.err.println("Found " + hits.totalHits + // 6
32 " document(s) (in " + (end - start) + // 6
33 " milliseconds) that matched query '" + // 6
34 q + "':"); // 6
35
36 for (ScoreDoc scoreDoc : hits.scoreDocs) {
37 Document doc = is.doc(scoreDoc.doc); // 7
38 System.out.println(doc.get("fullpath")); // 8
39 }
40
41 is.close(); // 9
42 }
43 }
同上操作,配置新的Java Application,如下图:
图:配置查询参数
点击运行,可以得到运行结果。
也就是我们上面索引的文件,当然,随着文件的多少及大小,速度会不同,这里只是一个演示程序,你可以根据你本身的程序自行设置查询条件。
索引过程中的几个核心类
IndexWriter
IndexWriter是索引过程的核心组件。用于创建一个新的索引并把文档加到已有的索引中去,也可以向索引中添加、删除和更新被索引文档的信息。
Directory
Directory类描述了Lucene索引的存放位置。
Analyzer
Analyzer是分词器接口,文本文件在被索引之前,需要经过Analyzer处理。常用的中文分词器有庖丁、IKAnalyzer等。
Document
Document对象代表一组域(Field)的集合。其实说白了就是文件,可能是文本文件,word或者pdf等。
Field
Field就是每个文档中包含的不同的域。
lucene构建索引的流程图如下:
图:lucene构建索引流程
搜索过程中的几个核心类
IndexSearcher
IndexSearcher是对前边IndexWriter创建的索引进行搜索。
Term
Term对象是搜索功能的基本单元,跟Field对象非常类似,可以放入我们查询的条件。
Query
Query就是Lucene给我们的查询接口,它有很多的子类,我们可以基于这些进行功能丰富的查询。
TermQuery
TermQuery是Lucene提供的最基本的查询类型。
TopDocs
TopDocs类是一个简单的指针容器,指针一般指向前N个排名的搜索结果,搜索结果即匹配查询条件的文档。
图:lucene查询请求流程
- CVE-2017-3085:Adobe Flash泄漏Windows用户凭证
- hbase源码系列(九)StoreFile存储格式
- 如何确定恶意软件是否在自己的电脑中执行过?
- Carbondata源码系列(二)文件格式详解
- 挖洞经验 | 记一次针对Twitter(Periscope)API 的有趣挖洞经历
- 设计模式学习(二): 观察者模式 (C#)
- Carbondata源码系列(一)文件生成过程
- BoopSuite:基于Python编写的无线安全审计套件
- 设计模式学习(一):多用组合少用继承(C#)
- 在asp.net web api 2 (ioc autofac) 使用 Serilog 记录日志
- hbase源码系列(十三)缓存机制MemStore与Block Cache
- hbase源码系列(十四)Compact和Split
- 设计模式学习(四): 1.简单工厂 (附C#实现)
- 从头编写 asp.net core 2.0 web api 基础框架 (5) EF CRUD
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法
- Spark Opeartor的指标体系
- R-基本绘图参数(Ⅰ)
- NVIDIA TensorRT Inference Server on Kubernetes
- Kubernetes 环境的 Tensorflow Serving on S3
- 数据处理|数据框重铸
- Go mod 常见问题(持续更新)
- R In Action|创建数据集
- R语言进阶之生存分析
- R In Action |基本数据管理
- R|apply,tapply
- python中的基本运算
- 助力联邦——Pulsar在Angel PowerFL联邦学习平台中的应用
- 让数据跃然“图”上!腾讯位置服务数据可视化API正式发布
- 腾讯云 Serverless 衔接 Kafka 上下游数据流转实战
- Tensorflow 测试一段能运行在 GPU 的代码