简介
概述
Lucene总的来说是:一个高效的,可扩展的,全文检索库。全部用Java实现,无须配置。仅支持纯文本文件的索引(Indexing)和搜索(Search)。不负责由其他格式的文件抽取纯文本文件,或从网络中抓取文件的过程。
全文检索
我们生活中的数据总体分为两种:结构化数据 和非结构化数据 。
结构化数据: 指具有固定格式或有限长度的数据,如数据库,元数据等。
非结构化数据: 指不定长或无固定格式的数据,如邮件,word文档等。
当然有的地方还会提到第三种,半结构化数据,如XML,HTML等,当根据需要可按结构化数据来处理,也可抽取出纯文本按非结构化数据来处理。
非结构化数据又一种叫法叫全文数据。
这种先建立索引,再对索引进行搜索的过程就叫全文检索(Full-text Search) 。
Lucene流程

说明Lucene 是有索引和搜索的两个过程,包含索引创建,索引,搜索三个要点。
让我们更细一些看Lucene的各组件:

- 被索引的文档用Document对象表示。
- IndexWriter 通过函数addDocument 将文档添加到索引中,实现创建索引的过程。
- Lucene 的索引是应用反向索引。
- 当用户有请求时,Query 代表用户的查询语句。
- IndexSearcher 通过函数search 搜索Lucene Index 。
- IndexSearcher 计算term weight 和score 并且将结果返回给用户。
返回给用户的文档集合用TopDocsCollector 表示。
实现
package test2;
import org.apache.lucene.analysis.Analyzer;
import org.apache.lucene.analysis.standard.StandardAnalyzer;
import org.apache.lucene.document.Document;
import org.apache.lucene.document.Field;
import org.apache.lucene.document.StringField;
import org.apache.lucene.document.TextField;
import org.apache.lucene.index.DirectoryReader;
import org.apache.lucene.index.IndexReader;
import org.apache.lucene.index.IndexWriter;
import org.apache.lucene.index.IndexWriterConfig;
import org.apache.lucene.queryparser.classic.ParseException;
import org.apache.lucene.queryparser.classic.QueryParser;
import org.apache.lucene.search.IndexSearcher;
import org.apache.lucene.search.Query;
import org.apache.lucene.search.ScoreDoc;
import org.apache.lucene.search.TopScoreDocCollector;
import org.apache.lucene.store.Directory;
import org.apache.lucene.store.RAMDirectory;
import org.apache.lucene.util.Version;
import java.io.IOException;
public class LuceneTest {
public static void main(String[] args) throws IOException, ParseException {
Analyzer analyzer = new StandardAnalyzer(Version.LUCENE_47);
//将索引存储到内存中
Directory directory = new RAMDirectory();
//如下想把索引存储到硬盘上,使用下面的代码代替
//Directory directory = FSDirectory.open(Paths.get("/tmp/testindex"));
//写入索引库
IndexWriterConfig config = new IndexWriterConfig(Version.LUCENE_47,analyzer);
IndexWriter iwriter = new IndexWriter(directory, config);
String[] texts = new String[]{
"Mybatis分页插件 - 示例",
"Mybatis 贴吧问答 第一期",
"Mybatis 示例之 复杂(complex)属性(property)",
"Mybatis极其(最)简(好)单(用)的一个分页插件",
"Mybatis 的Log4j日志输出问题 - 以及有关日志的所有问题",
"Mybatis 示例之 foreach (下)",
"Mybatis 示例之 foreach (上)",
"Mybatis 示例之 SelectKey",
"Mybatis 示例之 Association (2)",
"Mybatis 示例之 Association"
};
for (String text : texts) {
Document doc = new Document();
// doc.add(new Field("fieldname", text, TextField.TYPE_STORED));
doc.add(new TextField("title", text, Field.Store.YES));
doc.add(new StringField("isbn", ""+String.valueOf(Math.random()), Field.Store.YES));
iwriter.addDocument(doc);
}
iwriter.close();
//读取索引并查询
DirectoryReader reader = DirectoryReader.open(directory);
IndexSearcher isearcher = new IndexSearcher(reader);
//解析一个简单的查询
QueryParser parser = new QueryParser(Version.LUCENE_47,"title", analyzer);
Query query = parser.parse("foreach");
ScoreDoc[] hits = isearcher.search(query, 1000).scoreDocs;
//迭代输出结果
for (int i = 0; i < hits.length; i++) {
Document hitDoc = isearcher.doc(hits[i].doc);
System.out.println(hitDoc.get("title"));
System.out.println(hitDoc.get("isbn"));
}
reader.close();
directory.close();
}
}
Mybatis 示例之 foreach (下)
0.936427711899241
Mybatis 示例之 foreach (上)
0.025906583963816954