lucene,你也会(15篇)——第一篇 快速入门

简介:

日常开发中,相信大家经常会用like去匹配一些数据,同时我们也知道,like往往会导致全表扫描,当数据量越来越大的时候,我们会纠结于

数据库的龟速查找,此时我们必须另寻蹊跷,这时lucene就可以大显身手了。

首先我们做一个demo,向数据库中插入10w条数据,总共778M。

接下来,我们搜索下新闻内容中包含“流行”的记录。

mmd,检索一下要78s,是谁都要砸了面前的破机子。

下面我们来看看lucene的效果怎么样。下载地址:http://incubator.apache.org/lucene.net/download.html





using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Lucene.Net.Index;
using Lucene.Net.Store;
using Lucene.Net.Analysis.Standard;
using Lucene.Net.Documents;
using System.Data;
using System.Diagnostics;
using Lucene.Net.Search;

using Lucene.Net.QueryParsers;

namespace First
{
 class Program
 {
 static string path = @"D:\Sample";

 static void Main(string[] args)
 {
 //创建索引
 CreateIndex();

 var watch = Stopwatch.StartNew();

 //搜索
 IndexSearcher search = new IndexSearcher(path);

 //查询表达式
 QueryParser query = new QueryParser(string.Empty, new StandardAnalyzer());

 //query.parse:注入查询条件
 var hits = search.Search(query.Parse("Content:流行"));

 for (int i = 0; i < hits.Length(); i++)
 {
 Console.WriteLine("当前内容:{0}", hits.Doc(i).Get("Content").Substring(0, 20) + "...");
 }

 watch.Stop();

 Console.WriteLine("搜索耗费时间:{0}", watch.ElapsedMilliseconds);
 }

 static void CreateIndex()
 {
 //创建索引库目录
 var directory = FSDirectory.GetDirectory(path, true);

 //创建一个索引,采用StandardAnalyzer对句子进行分词
 IndexWriter indexWriter = new IndexWriter(directory, new StandardAnalyzer());

 var reader = DbHelperSQL.ExecuteReader("select * from News");

 while (reader.Read())
 {
 //域的集合:文档,类似于表的行
 Document doc = new Document();

 //要索引的字段
 doc.Add(new Field("ID", reader["ID"].ToString(), Field.Store.YES, Field.Index.NOT_ANALYZED));
 doc.Add(new Field("Title", reader["Title"].ToString(), Field.Store.NO, Field.Index.ANALYZED));
 doc.Add(new Field("Content", reader["Content"].ToString(), Field.Store.YES, Field.Index.ANALYZED));

 indexWriter.AddDocument(doc);
 }

 reader.Close();

 //对索引文件进行优化
 indexWriter.Optimize();

 indexWriter.Close();
 }
 }
}

我靠,448ms,顿时78s黯然失色,当然这个时间是不包含"创建索引“的时间,从时间复杂度上来说,这种预加载索引算是常量。

作为入门,简单的介绍下lucene的实现过程,首先lucene主要分成两步:"索引"和"搜索"。

一:索引:

相信大家对索引还是比较熟悉的,lucene能够将我们内容切分成很多词,然后将词作为key,建立“倒排索引”,然后放到索引库中,在上面

的例子中,我们看到了索引过程中使用到了IndexWriter,FSDirectory,StandardAnalyzer,Document和Field这些类,下面简要分析下。

1:IndexWriter

我们看到该类有一个AddDocument方法,所以我们认为该类实现了索引的写入操作。

2:FSDirectory

这个就更简单了,提供了索引库的存放位置,比如我们这里的D:\Sample,或许有人问,能不能存放在内存中,在强大的lucene面前当然

可以做到,lucene中的RAMDirectory就可以实现,当然我们的内存足够大的话,还是可以用内存承载索引库,进而提高搜索的效率。

3:StandardAnalyzer

这个算是索引过程中最最关键的一步,也是我们使用lucene非常慎重考虑的东西,之所以我们能搜索秒杀,关键在于我们如何将输入的内容

进行何种形式的切分,当然不同的切分形式诞生了不同的分析器,StandardAnalyzer就是一个按照单字分词的一种分析器,详细的介绍后续文

章分享。

4:Document

在上面的例子可以看到,他是承载field的集合,然后添加到IndexWriter中,有点类似表中的行的概念。

5: Field

提供了对要分析的字段进行何种处理,以KV形式呈现。

①:Field.Store.YES, Field.Index.NOT_ANALYZED 表示对索引字段采取:原样保存并且不被StandardAnalyzer进行切分。

②: Field.Store.NO, Field.Index.ANALYZED 不保存但是要被StandardAnalyzer切分。

二:搜索

这个比较容易,根据我们输入的词lucene能够在索引库中快速定位到我们要找的词,同样我们可以看到IndexSearcher,QueryParser,Hits。

1:IndexSearcher

这个我们可以理解成以只读的形式打开由IndexWriter创建的索引库,search给QueryParser提供了查询的桥梁。

2:QueryParser

这玩意提供了一个parse方法能够将我们要查找的词转化为lucene能够理解了查询表达式。

3:Hits

这个就是获取匹配结果的一个指针,优点类似C#中的延迟加载,目的都是一样,提高性能。


相关文章
|
6月前
|
索引
lucene入门使用
lucene入门使用
36 2
|
Java PHP 开发者
最佳正则表达式快速入门教程,看这篇就够了!
你都不知道正则表达式的作用是什么 怎么可能学好它呢? 来吧学习一下正则的基础知识吧!
57 0
最佳正则表达式快速入门教程,看这篇就够了!
|
Java 索引
04Lucene入门程序
04Lucene入门程序
52 0
|
存储 自然语言处理 JavaScript
【ElasticSearch从入门到放弃系列 三】Lucene的基本概念和使用(上)
【ElasticSearch从入门到放弃系列 三】Lucene的基本概念和使用(上)
144 1
|
自然语言处理 Java 索引
【ElasticSearch从入门到放弃系列 三】Lucene的基本概念和使用(下)
【ElasticSearch从入门到放弃系列 三】Lucene的基本概念和使用(下)
87 0
【ElasticSearch从入门到放弃系列 三】Lucene的基本概念和使用(下)
|
存储 网络协议 Java
C# 快速入门笔记
C# 快速入门笔记
C# 快速入门笔记
|
SQL JSON 自然语言处理
全文检索工具elasticsearch:第一章:理论知识
全文检索工具elasticsearch:第一章:理论知识
272 0
|
JSON 搜索推荐 Java
第三章 Elasticsearch简介
第三章 Elasticsearch简介
第三章 Elasticsearch简介
|
存储 自然语言处理 分布式计算
全文检索工具solr:第一章:理论知识
全文检索工具solr:第一章:理论知识
132 0
|
存储 搜索推荐 Java
史上最全的ElasticSearch系列之入门
前言 文本已收录至我的GitHub仓库,欢迎Star:github.com/bin39232820… 种一棵树最好的时间是十年前,其次是现在
295 0

相关实验场景

更多