版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/qq_33322074/article/details/89929836
文章目录
1. lucene学习笔记一
1.1. lucene的作用
- 实现文本搜索的框架,用于文本的搜索,非结构化文件的搜索。可以搜索文件里面的内容。用于电商网站上的搜索。
- 实现文本搜索首先要进行索引的创建,索引创建了才能实现文本搜索。
1.2. lucene的实现步骤
- 获取原始文档
- 通过爬虫爬取,并存储下来。
- 创建文档对象
- 每个文档有多个域,包含:文件名,路径,内容,大小。
- 每个文档都有一个编号。
- 分析文档
- 将大写转为小写,去除标点,停用词等最终生成语汇单元。每个语汇单元里的单词叫做一个term
- 不同域中即使term一样也不是同一个term.
- 必须是在同一个域中,并且一样才是一个term.
- 创建索引
- 索引库包含两个方面:一个是索引内容,一个是文件对象。
- 通过对获取的原始文档进行分析,然后分析出term,并创建文档的对象域。
- 将分析出的term存入索引库,将文档的对象存入索引库。
- 创建索引,
- 搜索时,执行查询,获取文档结果。
1.3. lucene案例学习
- 创建java工程
- 导入包
- lucene核心包
- lucene分析词包
- lucene查询包
- io流包
- junit测试包
- 创建索引
- 虽然步骤第一步不是创建索引,但是我们应该倒着推,因为,创建索引和索引库相连,自然最应该先想到
- 包含两个参数,一个是创建的索引保存路径,一个是需要索引参数,
- indexWriter是一个索引写入流,需要关闭
IndexWriter indexWriter=new IndexWriter(directory, indexWriterConfig);
- 创建索引保存路径
- 如果没有该路径会自动创建。
Directory directory =FSDirectory.open(new File("d:\\luceneindex\\index"));
- 配置索引写入流的参数
- 包含一个版本,一个文字分析器
- 实例化一个分析器。注意是抽象类需要子类实例化。
Analyzer analyzer=new StandardAnalyzer();
IndexWriterConfig indexWriterConfig=new IndexWriterConfig(Version.LATEST, analyzer);
- 创建一个Document文件,这个文件用来专门存储各种域对象
Document document=new Document();
- 通过文件流的输入获取要分析的资源,并将资源存储到数组中
File file=new File("D:\\luceneindex\\searchsource");
File[] listFiles = file.listFiles();
- for增强循环遍历该数组
- 获取文件的名字,路径,大小,内容,并存储到各个域中。
- 注意,不同的内容存储不同的域,存储的域要表明,名字,要存储的对象,是否存储到索引中
for(File file2:listFiles) {
//文件名称
String file_name=file2.getName();
Field fileNameField=new TextField("fileName",file_name,Store.YES);
//文件大小
long file_size = FileUtils.sizeOf(file2);
Field fileSizeField=new LongField("fileSize", file_size, Store.YES);
//文件路径
String file_path = file2.getPath();
Field filePathField=new StoredField("filePath", file_path);
//文件内容
String file_context = FileUtils.readFileToString(file2);
Field fileContextField=new TextField("fileContext", file_context,Store.YES);
- 将所有域对象存储到document文档中
- 主要是为了统一管理
document.add(fileContextField);
document.add(filePathField);
document.add(fileSizeField);
document.add(fileNameField);
- 使用indexWriter对象将document中的内容添加到索引库中,并将索引也添加到了索引库
//使用indexWriter对象将document对象写入索引库,此时进行索引创建,并将索引和document对象写入索引库。
indexWriter.addDocument(document);
- 关闭indexWriter流
- 完成索引的创建。
//关流
indexWriter.close();
1.4. 查询索引
- 创建一个Directory对象,获取索引所在路径
//第一步:创建一个Directory对象,获取索引库存放的位置。
Directory directory=FSDirectory.open(new File("d:\\luceneindex\\index"));
- 创建索引读取流
//第二步;创建一个indexReader索引读取流,指定Directory路径
IndexReader indexReader=DirectoryReader.open(directory);
- 创建索引查找对象并指定查找的内容,即:读取的内容
//第三步:indexSearcher对象,需要指定IndexReader对象
IndexSearcher indexSearcher=new IndexSearcher(indexReader);
- 创建一个TermQuery对象指定查询的关键词
//第四步:创建一个TermQuery对象,指定查询的域和关键词
Query query=new TermQuery(new Term("fileName","apache"));
- 执行查询
- 并返回n条记录
//第五步:执行查询
TopDocs topDocs = indexSearcher.search(query, 2);
- 返回查询结果
//第六步:返回查询结果,遍历查询结果并输出
ScoreDoc[] scoreDocs = topDocs.scoreDocs;
- 遍历查询结果
- 通过结果中的id值,将查询的内容返回到文件对象中
- 通过文件对象获取文件中的内容。
for(ScoreDoc scoreDoc:scoreDocs) {
int doc = scoreDoc.doc;
Document document=indexSearcher.doc(doc);
//文件名
String fileName=document.get("fileName");
System.out.println(fileName);
String fileContext=document.get("fileContext");
System.out.println(fileContext);
String fileSize=document.get("fileSize");
System.out.println(fileSize);
String filePath=document.get("filePath");
System.out.println(filePath);
}
- 关闭流
//第七步:关闭indexReader流
indexReader.close();
- 搜索使用的分析器和索引使用的分析器要一致。
1.5. 索引的删除
- 创建一个IndexWriter对象,注意这个对象是包含索引存储路径,和所使用分析器的对象。
public IndexWriter getIndexWriter() throws Exception{
Directory directory = FSDirectory.open(new File("D:\\temp\\index"));
// Directory directory = new RAMDirectory();//保存索引到内存中 (内存索引库)
Analyzer analyzer = new StandardAnalyzer();// 官方推荐
IndexWriterConfig config = new IndexWriterConfig(Version.LATEST, analyzer);
return new IndexWriter(directory, config);
}
- 删除文档
//全删除
@Test
public void testAllDelete() throws Exception {
IndexWriter indexWriter = getIndexWriter();
indexWriter.deleteAll();
indexWriter.close();
}
- 条件删除
//根据条件删除
@Test
public void testDelete() throws Exception {
IndexWriter indexWriter = getIndexWriter();
Query query = new TermQuery(new Term("fileName","apache"));
indexWriter.deleteDocuments(query);
indexWriter.close();
}
1.6. 修改索引
- 使用updateDocument方法
- 修改的是域对象
//修改
@Test
public void testUpdate() throws Exception {
IndexWriter indexWriter = getIndexWriter();
Document doc = new Document();
doc.add(new TextField("fileN", "测试文件名",Store.YES));
doc.add(new TextField("fileC", "测试文件内容",Store.YES));
indexWriter.updateDocument(new Term("fileName","lucene"), doc, new IKAnalyzer());
indexWriter.close();
}
1.7. 查询索引
- 查询所有:使用MatchAllDocsQuery类
- printResult是一个方法。打印的方法。
//查询所有
@Test
public void testMatchAllDocsQuery() throws Exception {
IndexSearcher indexSearcher = getIndexSearcher();
Query query = new MatchAllDocsQuery();
System.out.println(query);
printResult(indexSearcher, query);
//关闭资源
indexSearcher.getIndexReader().close();
}
- 精确查询:TermQuery
- 根据数值范围查询
//根据数值范围查询
@Test
public void testNumericRangeQuery() throws Exception {
IndexSearcher indexSearcher = getIndexSearcher();
//false是不包含左边区间,true是包含右边区间
Query query = NumericRangeQuery.newLongRange("fileSize", 47L, 200L, false, true);
System.out.println(query);
printResult(indexSearcher, query);
//关闭资源
indexSearcher.getIndexReader().close();
}
- 组合查询
- BooleanQuery
//可以组合查询条件
@Test
public void testBooleanQuery() throws Exception {
IndexSearcher indexSearcher = getIndexSearcher();
BooleanQuery booleanQuery = new BooleanQuery();
Query query1 = new TermQuery(new Term("fileName","apache"));
Query query2 = new TermQuery(new Term("fileName","lucene"));
// select * from user where id =1 or name = 'safdsa'
booleanQuery.add(query1, Occur.MUST);//必须,该名字上必须有apache
booleanQuery.add(query2, Occur.SHOULD);//非必须,可以没有
System.out.println(booleanQuery);
printResult(indexSearcher, booleanQuery);
//关闭资源
indexSearcher.getIndexReader().close();
}
1.8. 使用解析查询
- 利用QueryParser查询
//条件解释的对象查询
@Test
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();
}
- 多个默认查询域
- 使用MultiFieldQueryParser
//条件解析的对象查询 多个默念域
@Test
public void testMultiFieldQueryParser() throws Exception {
IndexSearcher indexSearcher = getIndexSearcher();
String[] fields = {"fileName","fileContent"};
//参数1: 默认查询的域
//参数2:采用的分析器
MultiFieldQueryParser queryParser = new MultiFieldQueryParser(fields,new IKAnalyzer());
// *:* 域:值
Query query = queryParser.parse("lucene is apache");
printResult(indexSearcher, query);
//关闭资源
indexSearcher.getIndexReader().close();
}