Lucene入门操做(简单的CRUD)

Lucene是一个很是优秀的开源的全文搜索引擎(架构),咱们能够在它的上面开发出各类全文搜索的应用来。
直接上代码:java

jar包

这里写图片描述

建立索引库

@Test
    //建立索引库
    public void testCreateIndex() throws Exception {
// 第一步:建立一个indexwriter对象。
// 1)指定索引库的存放位置Directory对象
        Directory directory = FSDirectory.open(new File("D:\\temp\\index"));
        //若要将索引库放在内存中
// Directory directory = new RAMDirectory();
// 2)指定一个分析器,对文档内容进行分析。
// Analyzer analyzer = new StandardAnalyzer();
        Analyzer analyzer = new IKAnalyzer();   //中文支持 注意搜索时也要使用IKAnalyzer
        IndexWriterConfig config = new IndexWriterConfig(Version.LATEST, analyzer);
        IndexWriter indexWriter = new IndexWriter(directory, config);
// 第三步:建立field对象,将field添加到document对象中。
        //1.读取文档所在目录
        File file = new File("D:\\搜狗高速下载\\黑马javaEE\\【阶段15】luncene、Solr使用\\Lucene&solr\\01.参考资料\\searchsource");
        File[] files = file.listFiles();
        for (File f : files) {
// 第二步:建立document对象。
            Document document = new Document();
            //2.获取每一个文件的field
            String file_name = f.getName();
            Field fileName = new TextField("fileName", file_name, Store.YES);
            String file_path = f.getPath();
            Field filePath = new StoredField("filePath", file_path);
            Long file_size = FileUtils.sizeOf(f);
            Field fileSize = new LongField("fileSize", file_size, Store.YES);
            String file_content = FileUtils.readFileToString(f);
            Field fileContent = new TextField("fileContent", file_content, Store.YES);
// 3.添加field到document中
            document.add(fileName);
            document.add(filePath);
            document.add(fileSize);
            document.add(fileContent);
// 第四步:使用indexwriter对象将document对象写入索引库,此过程进行索引建立。并将索引和document对象写入索引库。
            indexWriter.addDocument(document);
        }
// 第五步:关闭IndexWriter对象。
        indexWriter.close();
    }

删除索引

//得到IndexWriter
    public IndexWriter getIndexWriter() throws Exception {
        Directory directory = FSDirectory.open(new File("D:\\temp\\index"));
        Analyzer analyzer = new IKAnalyzer();
        IndexWriterConfig config = new IndexWriterConfig(Version.LATEST, analyzer);
        return new IndexWriter(directory, config);
    }

    @Test
    //删除所有索引库
    public void testDeleteAll() throws Exception {
        IndexWriter indexWriter = getIndexWriter();
        indexWriter.deleteAll();
        indexWriter.close();
    }

    @Test
    //根据field删除索引
    public void testDelete() throws Exception {
        IndexWriter indexWriter = getIndexWriter();
        Term t = new Term("fileName", "apache");
        Query query = new TermQuery(t);
        indexWriter.deleteDocuments(query);
        indexWriter.close();
    }

修改索引

@Test
    //索引库修改 --先删除在添加
    public void testUpdate() throws Exception {
        IndexWriter indexWriter = getIndexWriter();
        Term delTerm = new Term("fileName", "apache");
        Document doc = new Document();
        doc.add(new TextField("fileN", "测试文件名", Store.YES));
        doc.add(new TextField("fileC", "测试文件内容", Store.YES));
        indexWriter.updateDocument(delTerm, doc, new IKAnalyzer());
        indexWriter.close();
    }

查询索引

1、使用Query的子类查询
TermQuery: 经过Field和关键词查询web

//根据索引查询数据
    @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对象,指定查询的域和查询的关键词。
        Term term = new Term("fileName", "apache");
// Term term = new Term("fileN", "测试文件名");
        TermQuery termQuery = new TermQuery(term);
// 第五步:执行查询。
        TopDocs topDocs = indexSearcher.search(termQuery, 2);
// 第六步:返回查询结果。遍历查询结果并输出。
        ScoreDoc[] scoreDocs = topDocs.scoreDocs;//此时查询到的是索引表中的文档ID数组
        for (ScoreDoc scoreDoc : scoreDocs) {
            System.out.println("文件信息:");
            int doc = scoreDoc.doc; //文档ID
            //根据文档ID拿到文档对象
            Document document = indexSearcher.doc(doc);
            System.out.println(document.get("fileName"));
            System.out.println(document.get("filePath"));
            System.out.println(document.get("fileSize"));
            System.out.println(document.get("fileContent"));
        }
// 第七步:关闭IndexReader对象
        indexReader.close();
    }

MatchAllQuery:查询全部apache

//得到indexSeacher
    public IndexSearcher getIndexSearcher() throws Exception {
        Directory directory = FSDirectory.open(new File("D:\\temp\\index"));
        IndexReader indexReader = DirectoryReader.open(directory); 
        return new IndexSearcher(indexReader);
    }

    //打印查询结果
    public void printResult(Query query, IndexSearcher indexSearcher) throws Exception {
        TopDocs topDocs = indexSearcher.search(query, 10);
        ScoreDoc[] scoreDocs = topDocs.scoreDocs;
        for (ScoreDoc scoreDoc : scoreDocs) {
            int docID = scoreDoc.doc;
            Document doc = indexSearcher.doc(docID);
            System.out.println(doc.get("fileName"));
        }
    }

    //查询全部 MatchAllDocsQuery
    @Test
    public void testQueryAll() throws Exception {
        IndexSearcher indexSearcher = getIndexSearcher();
        Query query = new MatchAllDocsQuery();
        printResult(query, indexSearcher);
        indexSearcher.getIndexReader().close();
    }

NumericRangeQuery:根据数值范围查询
范围查询在lucene中支持数值类型,不支持字符串类型。在solr中支持字符串类型。数组

//根据数值范围查询 --NumericRangeQuery.newLongRange("fileSize", 47L, 200L, true, true)
    @Test                                           //field域,最小值,最大值,是否包含最大最小值
    public void testNumericRangeQuery() throws Exception {
        IndexSearcher indexSearcher = getIndexSearcher();
        Query query = NumericRangeQuery.newLongRange("fileSize", 47L, 200L, true, true);
        printResult(query, indexSearcher);
        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 = NumericRangeQuery.newLongRange("fileSize", 47L, 200L, true, false);
        booleanQuery.add(query1, Occur.MUST);     //必须
        booleanQuery.add(query2, Occur.MUST_NOT); //必须不
// booleanQuery.add(query2, Occur.SHOULD); //都行 --恕我直言,真是睿智
        printResult(booleanQuery, indexSearcher);
        indexSearcher.getIndexReader().close();
    }

2、使用QueryParse查询svg

1.QueryParse
主要经过queryParse.parse(“:“)方法的参数表达式来决定查询类型
基本查询: field : 关键字
查询所有: * : *
范围查询: field : [max TO min}
注意中间空格。括号觉得左闭右开。与区间的用法是同样的
组合条件查询: +field:关键字 +field:关键字
+ :OCCUR.MUST - :OCCUR.MUST_NOT 不写就是OCCUR.SHOULD测试

@Test
    //使用Queryparse查询
    public void testQueryParse() throws Exception {
        IndexSearcher indexSearcher = getIndexSearcher();
        QueryParser queryParse = new QueryParser("fileName", new IKAnalyzer());
        Query query = queryParse.parse("*:*");//查询所有
        printResult(query, indexSearcher);
        indexSearcher.getIndexReader().close();
    }

2.MultiFieldQueryParse:多默认域查询–没吉尔用搜索引擎

@Test
    //多默认域查询
    public void testMultiFieldQueryParse() throws Exception {
        IndexSearcher indexSearcher = getIndexSearcher();
        String[] fields = {"fileName","fileContent"};
        MultiFieldQueryParser queryParse = new MultiFieldQueryParser(fields, new IKAnalyzer());
        Query query = queryParse.parse("fileName:apache");//查询所有
        printResult(query, indexSearcher);
        indexSearcher.getIndexReader().close();
    }