一、Lucene是什么
Lucene是apache下的一个开放源代码的全文检索引擎工具包。提供了完整的查询引擎和索引引擎,部分文本分析引擎。Lucene的目的是为软件开发人员提供一个简单易用的工具包,以方便的在目标系统中实现全文检索的功能。
1.2 Lucene实现全文检索的流程*
这种先建立索引,再对索引进行搜索的过程就叫全文检索(Full-text Search)。
核心Ducument、Field、term
在索引前需要将原始内容创建成文档(Document),文档中包括一个一个的域(Field),域中存储内容可以理解为在数据库中插入数据
不同的域中拆分出来的相同的单词是不同的term。term中包含两部分一部分是文档的域名,另一部分是单词的内容*(从Field提取信息拆分为关键词)**
Document — 表
Field — 表中数据
注意:每个Document可以有多个Field,不同的Document可以有不同的Field,同一个Document可以有相同的Field(域名和域值都相同)
每个文档都有一个唯一的编号,就是文档id(查询的结果)。
二、索引的增伤查改
jar包
Lucene包:
lucene-core-4.10.3.jar
lucene-analyzers-common-4.10.3.jar
lucene-queryparser-4.10.3.jar
其它:
commons-io-2.4.jar
junit-4.9.jar
2.1创建索引
public void testIndex() throws Exception {
// 第一步:创建一个java工程,并导入jar包。
// 第二步:创建一个indexwriter对象。
Directory directory = FSDirectory.open(new File("D:\\temp\\index"));
// Directory directory = new RAMDirectory();//保存索引到内存中 (内存索引库)
// Analyzer analyzer = new StandardAnalyzer();// 官方推荐
Analyzer analyzer = new IKAnalyzer();// 官方推荐
IndexWriterConfig config = new IndexWriterConfig(Version.LATEST, analyzer);
IndexWriter indexWriter = new IndexWriter(directory, config);
// 1)指定索引库的存放位置Directory对象
// 2)指定一个分析器,对文档内容进行分析。
// 第三步:创建field对象,将field添加到document对象中。
File f = new File("D:\\Lucene&solr\\searchsource");
File[] listFiles = f.listFiles();
for (File file : listFiles) {
// 第三步:创建document对象。
Document document = new Document();
// 文件名称
String file_name = file.getName();
Field fileNameField = new TextField("fileName", file_name, Store.YES);
// 文件大小
long file_size = FileUtils.sizeOf(file);
Field fileSizeField = new LongField("fileSize", file_size, Store.YES);
// 文件路径
String file_path = file.getPath();
Field filePathField = new StoredField("filePath", file_path);
// 文件内容
String file_content = FileUtils.readFileToString(file);
Field fileContentField = new TextField("fileContent", file_content, Store.NO);
document.add(fileNameField);
document.add(fileSizeField);
document.add(filePathField);
document.add(fileContentField);
// 第四步:使用indexwriter对象将document对象写入索引库,此过程进行索引创建。并将索引和document对象写入索引库。
indexWriter.addDocument(document);
}
// 第五步:关闭IndexWriter对象。
indexWriter.close();
}
2.1.1. IKAnalyzer分析器使用
使用方法:
第一步:把jar包添加到工程中
第二步:把配置文件和扩展词典和停用词词典添加到classpath下
2.2搜索索引
// 搜索索引
@Test
public void testSearch() throws Exception {
// 第一步:创建一个Directory对象,也就是索引库存放的位置。
Directory directory = FSDirectory.open(new File("D:\\temp\\index"));// 磁盘
// 第二步:创建一个indexReader对象,需要指定Directory对象。
IndexReader indexReader = DirectoryReader.open(directory);
// 第三步:创建一个indexsearcher对象,需要指定IndexReader对象
IndexSearcher indexSearcher = new IndexSearcher(indexReader);
// 第四步:创建一个TermQuery对象,指定查询的域和查询的关键词。
Query query = new TermQuery(new Term("fileName", "lucene"));
// 第五步:执行查询。
TopDocs topDocs = indexSearcher.search(query, 10);
// 第六步:返回查询结果。遍历查询结果并输出。
ScoreDoc[] scoreDocs = topDocs.scoreDocs;
for (ScoreDoc scoreDoc : scoreDocs) {
int doc = scoreDoc.doc;
Document document = indexSearcher.doc(doc);
// 文件名称
String fileName = document.get("fileName");
System.out.println(fileName);
// 文件内容
String fileContent = document.get("fileContent");
System.out.println(fileContent);
// 文件大小
String fileSize = document.get("fileSize");
System.out.println(fileSize);
// 文件路径
String filePath = document.get("filePath");
System.out.println(filePath);
System.out.println("------------");
}
// 第七步:关闭IndexReader对象
indexReader.close();
}
2.3删除索引
public void deleteAllIndex() throws IOException {
IndexWriter indexWriter = getIndexWriter();
//创建一个查询条件
indexWriter.deleteAll();
//关闭indexWriter
indexWriter.close();
}
//根据条件删除
public void deleteIndexByQuery() throws IOException {
IndexWriter indexWriter = getIndexWriter();
//创建一个查询条件
TermQuery query = new TermQuery(new Term("filename", "apache"));
//根据查询条件删除
indexWriter.deleteDocuments(query);
//关闭indexWriter
indexWriter.close();
}
2.4更改索引
public void updateIndex() throws IOException {
IndexWriter indexWriter = getIndexWriter();
//创建一个Document对象
Document document = new Document();
//想Document中添加不同的域
document.add(new TextField("fileName","要更改的内容",Store.YES));
indexWriter.updateDocument(new Term("content","java"),document);
//关闭indexWriter
indexWriter.close();
三、索引查询分类
3.1子类查询
3.1.1精确查询
Query query = new TermQuery(new Term(“name”, “lucene”));
3.1.2查询所有
MatchAllDocsQuery query = new MatchAllDocsQuery();
3.1.3数据范围查询
NumericRangeQuery query = NumericRangeQuery.newLongRange(“fileSize”, 47L, 200L, false, true);
3.1.4组合查询
BooleanQuery booleanQuery = new BooleanQuery();
3.2解析查询
public IndexSearcher getIndexSearcher() throws Exception{
// 第一步:创建一个Directory对象,也就是索引库存放的位置。
Directory directory = FSDirectory.open(new File("D:\\temp\\index"));// 磁盘
// 第二步:创建一个indexReader对象,需要指定Directory对象。
IndexReader indexReader = DirectoryReader.open(directory);
// 第三步:创建一个indexsearcher对象,需要指定IndexReader对象
return new IndexSearcher(indexReader);
}
public void printResult(IndexSearcher indexSearcher,Query query) throws IOException {
//第五步:执行查询
TopDocs topDocs = indexSearcher.search(query, 10);
//第六步:放回查询结果,遍历查询结果并输出
ScoreDoc[] scoreDocs = topDocs.scoreDocs;
for (ScoreDoc scoreDoc : scoreDocs) {
int doc = scoreDoc.doc;
Document document = indexSearcher.doc(doc);
//文件名称
String fileName = document.get("fileName");
System.out.println(fileName);
//文件内容
String fileContent = document.get("fileContent");
System.out.println(fileContent);
//文件大小
String fileSize = document.get("fileSize");
System.out.println(fileSize);
//文件路径
String filePath = document.get("filePath");
System.out.println(filePath);
System.out.println("----------------------");
}
}
//条件解释的对象查询
public void testQueryParser() throws Exception {
IndexSearcher indexSearcher = getIndexSearcher();
//参数1: 默认查询的域
//参数2:采用的分析器
QueryParser queryParser = new QueryParser("fileName",new IKAnalyzer());
// *:* 域:值
Query query = queryParser.parse("fileName:lucene is apache OR fileContent:lucene is apache");
printResult(indexSearcher, query);
//关闭资源
indexSearcher.getIndexReader().close();
}
附、解析查询语法
查询语法
1、基础的查询语法,关键词查询:
域名+“:”+搜索的关键字
例如:content:java
2、范围查询
域名+“:”+[最小值 TO 最大值]
例如:size:[1 TO 1000]
范围查询在lucene中支持数值类型,不支持字符串类型。在solr中支持字符串类型。
3、组合条件查询
1)+条件1 +条件2:两个条件之间是并且的关系and
例如:+filename:apache +content:apache
2)+条件1 条件2:必须满足第一个条件,应该满足第二个条件
例如:+filename:apache content:apache
3)条件1 条件2:两个条件满足其一即可。
例如:filename:apache content:apache
4)-条件1 条件2:必须不满足条件1,要满足条件2