Lucene 工作原理

Lucene是一个高性能的java全文检索工具包,它使用的是倒排文件索引结构。该结构及相应的生成算法如下:
  
  0)设有两篇文章1和2
  文章1的内容为:Tom lives in Guangzhou,I live in Guangzhou too.
  文章2的内容为:He once lived in Shanghai.
  
  1)由于lucene是基于关键词索引和查询的,首先我们要取得这两篇文章的关键词,通常我们需要如下处理措施
  a.我们现在有的是文章内容,即一个字符串,我们先要找出字符串中的所有单词,即分词。英文单词由于用空格分隔,比较好处理。中文单词间是连在一起的需要特殊的分词处理。
  b.文章中的”in”, “once” “too”等词没有什么实际意义,中文中的“的”“是”等字通常也无具体含义,这些不代表概念的词可以过滤掉
  c.用户通常希望查“He”时能把含“he”,“HE”的文章也找出来,所以所有单词需要统一大小写。
  d.用户通常希望查“live”时能把含“lives”,“lived”的文章也找出来,所以需要把“lives”,“lived”还原成“live”
  e.文章中的标点符号通常不表示某种概念,也可以过滤掉
  在lucene中以上措施由Analyzer类完成
  
  经过上面处理后
   文章1的所有关键词为:[tom] [live] [guangzhou] [live] [guangzhou]
   文章2的所有关键词为:[he] [live] [shanghai]
  
  2) 有了关键词后,我们就可以建立倒排索引了。上面的对应关系是:“文章号”对“文章中所有关键词”。倒排索引把这个关系倒过来,变成:“关键词”对“拥有该关键词的所有文章号”。文章1,2经过倒排后变成
  关键词               文章号
  guangzhou         1
  he                     2
  i                        1
  live                    1,2
  shanghai            2
  tom                   1
  
  通常仅知道关键词在哪些文章中出现还不够,我们还需要知道关键词在文章中出现次数和出现的位置,通常有两种位置:a)字符位置,即记录该词是文章中第几个字符(优点是关键词亮显时定位快);b)关键词位置,即记录该词是文章中第几个关键词(优点是节约索引空间、词组(phase)查询快),lucene 中记录的就是这种位置。
  
  加上“出现频率”和“出现位置”信息后,我们的索引结构变为:


  关键词             文章号[出现频率]                     出现位置
  guangzhou        1[2]                                        3,6
  he                     2[1]                                       1
  i                        1[1]                                       4
  live                    1[2],2[1]                                 2,5,2
  shanghai            2[1]                                       3
  tom                   1[1]                                        1
  
  以live 这行为例我们说明一下该结构:live在文章1中出现了2次,文章2中出现了一次,它的出现位置为“2,5,2”这表示什么呢?我们需要结合文章号和出现频率来分析,文章1中出现了2次,那么“2,5”就表示live在文章1中出现的两个位置,文章2中出现了一次,剩下的“2”就表示live是文章2中第 2个关键字。
  
  以上就是lucene索引结构中最核心的部分。我们注意到关键字是按字符顺序排列的(lucene没有使用B树结构),因此lucene可以用二元搜索算法快速定位关键词。
  
  实现时 lucene将上面三列分别作为词典文件(Term Dictionary)、频率文件(frequencies)、位置文件 (positions)保存。其中词典文件不仅保存有每个关键词,还保留了指向频率文件和位置文件的指针,通过指针可以找到该关键字的频率信息和位置信息。
  
   Lucene中使用了field的概念,用于表达信息所在位置(如标题中,文章中,url中),在建索引中,该field信息也记录在词典文件中,每个关键词都有一个field信息(因为每个关键字一定属于一个或多个field)。
  
  为了减小索引文件的大小,Lucene对索引还使用了压缩技术。首先,对词典文件中的关键词进行了压缩,关键词压缩为<堉?缀长度,后缀>,例如:当前词为“阿拉伯语”,上一个词为“阿拉伯”,那么“阿拉伯语”压缩为<3,语>。其次大量用到的是对数字的压缩,数字只保存与上一个值的差值(这样可以减小数字的长度,进而减少保存该数字需要的字节数)。例如当前文章号是16389(不压缩要用3个字节保存),上一文章号是16382,压缩后保存7(只用一个字节)。
  
   下面我们可以通过对该索引的查询来解释一下为什么要建立索引。
  假设要查询单词 “live”,lucene先对词典二元查找、找到该词,通过指向频率文件的指针读出所有文章号,然后返回结果。词典通常非常小,因而,整个过程的时间是毫秒级的。
  而用普通的顺序匹配算法,不建索引,而是对所有文章的内容进行字符串匹配,这个过程将会相当缓慢,当文章数目很大时,时间往往是无法忍受的。




本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/geekwang/archive/2008/11/29/3410187.aspx是一个高性能的java全文检索工具包,它使用的是倒排文件索引结构。该结构及相应的生成算法如下:
  现在也是c#的全文检索工具包了,所以都一样的。
  0)设有两篇文章1和2
  文章1的内容为:Tom lives in Guangzhou,I live in Guangzhou too.
  文章2的内容为:He once lived in Shanghai.
  
  1)由于lucene是基于关键词索引和查询的,首先我们要取得这两篇文章的关键词,通常我们需要如下处理措施
  a.我们现在有的是文章内容,即一个字符串,我们先要找出字符串中的所有单词,即分词。英文单词由于用空格分隔,比较好处理。中文单词间是连在一起的需要特殊的分词处理。
  b.文章中的”in”, “once” “too”等词没有什么实际意义,中文中的“的”“是”等字通常也无具体含义,这些不代表概念的词可以过滤掉
  c.用户通常希望查“He”时能把含“he”,“HE”的文章也找出来,所以所有单词需要统一大小写。
  d.用户通常希望查“live”时能把含“lives”,“lived”的文章也找出来,所以需要把“lives”,“lived”还原成“live”
  e.文章中的标点符号通常不表示某种概念,也可以过滤掉
  在lucene中以上措施由Analyzer类完成
  
  经过上面处理后
   文章1的所有关键词为:[tom] [live] [guangzhou] [live] [guangzhou]
   文章2的所有关键词为:[he] [live] [shanghai]
  
  2) 有了关键词后,我们就可以建立倒排索引了。上面的对应关系是:“文章号”对“文章中所有关键词”。倒排索引把这个关系倒过来,变成:“关键词”对“拥有该关键词的所有文章号”。文章1,2经过倒排后变成
  关键词               文章号
  guangzhou         1
  he                     2
  i                        1
  live                    1,2
  shanghai            2
  tom                   1
  
  通常仅知道关键词在哪些文章中出现还不够,我们还需要知道关键词在文章中出现次数和出现的位置,通常有两种位置:a)字符位置,即记录该词是文章中第几个字符(优点是关键词亮显时定位快);b)关键词位置,即记录该词是文章中第几个关键词(优点是节约索引空间、词组(phase)查询快),lucene 中记录的就是这种位置。
  
  加上“出现频率”和“出现位置”信息后,我们的索引结构变为:


  关键词             文章号[出现频率]                     出现位置
  guangzhou        1[2]                                        3,6
  he                     2[1]                                       1
  i                        1[1]                                       4
  live                    1[2],2[1]                                 2,5,2
  shanghai            2[1]                                       3
  tom                   1[1]                                        1
  
  以live 这行为例我们说明一下该结构:live在文章1中出现了2次,文章2中出现了一次,它的出现位置为“2,5,2”这表示什么呢?我们需要结合文章号和出现频率来分析,文章1中出现了2次,那么“2,5”就表示live在文章1中出现的两个位置,文章2中出现了一次,剩下的“2”就表示live是文章2中第 2个关键字。
  
  以上就是lucene索引结构中最核心的部分。我们注意到关键字是按字符顺序排列的(lucene没有使用B树结构),因此lucene可以用二元搜索算法快速定位关键词。
  
  实现时 lucene将上面三列分别作为词典文件(Term Dictionary)、频率文件(frequencies)、位置文件 (positions)保存。其中词典文件不仅保存有每个关键词,还保留了指向频率文件和位置文件的指针,通过指针可以找到该关键字的频率信息和位置信息。
  
   Lucene中使用了field的概念,用于表达信息所在位置(如标题中,文章中,url中),在建索引中,该field信息也记录在词典文件中,每个关键词都有一个field信息(因为每个关键字一定属于一个或多个field)。
  
  为了减小索引文件的大小,Lucene对索引还使用了压缩技术。首先,对词典文件中的关键词进行了压缩,关键词压缩为<堉?缀长度,后缀>,例如:当前词为“阿拉伯语”,上一个词为“阿拉伯”,那么“阿拉伯语”压缩为<3,语>。其次大量用到的是对数字的压缩,数字只保存与上一个值的差值(这样可以减小数字的长度,进而减少保存该数字需要的字节数)。例如当前文章号是16389(不压缩要用3个字节保存),上一文章号是16382,压缩后保存7(只用一个字节)。
  
   下面我们可以通过对该索引的查询来解释一下为什么要建立索引。
  假设要查询单词 “live”,lucene先对词典二元查找、找到该词,通过指向频率文件的指针读出所有文章号,然后返回结果。词典通常非常小,因而,整个过程的时间是毫秒级的。
  而用普通的顺序匹配算法,不建索引,而是对所有文章的内容进行字符串匹配,这个过程将会相当缓慢,当文章数目很大时,时间往往是无法忍受的。




本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/geekwang/archive/2008/11/29/3410187.aspx

转载于:https://www.cnblogs.com/dewin/archive/2009/11/24/1609905.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/381181.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

导出excel数字前面的0消失_EXCEL文本之王TEXT函数的4个运用

转自EXCEL不加班今天分享文本之王TEXT函数的4个运用&#xff0c;跟着卢子一起来操作。1.发票号都是8位&#xff0c;从系统导出后前面的0消失&#xff0c;如何补齐&#xff1f;常规格式发票号前面的0都会消失&#xff0c;只有文本格式情况下的0才不会消失。事先录入的话&#xf…

c 语言读取注册表信息,C++读取注册表的实现方法

C读取注册表GetRegValue.h:#ifndef __GETREGVALUE_H__#define __GETREGVALUE_H__#include //---------------------------------------------------------------//function:// GetRegValue 获取注册表中指定键的值//Access:// public//Parameter:// [in] int nKeyType - 注册表…

java传值问题.

Java传递参数只有一种 &#xff1a;值传递 而没有引用传递 一般根据传递类型来分类 可以分为 值类型数据 和 引用数据类型 值类型是原始数据类型 包括 int,byte,char short long,boolean,float,double 引用类型就是一般的class类 当然也包括原始数据的封装类型 比如int的 封装类…

stm32按键矩阵代码_STM32 学习笔记---1

既然打算学&#xff0c;基础的东西元件的得知道是什么&#xff0c;这样写代码的时候才能知道自己在干什么&#xff01;ROM 和Flash 断电后都能储存数据&#xff0c;RAM则不能其实闪存&#xff08;flash&#xff09;是ROM的一种它的全名---FLASH EEPROM EEPROM---电可擦除可编程…

c语言 包络算法,包络检测C程序

最近做项目要提取一个声音信号的包络波形&#xff0c;所以花了点时间研究各种包络提取的算法。所谓包络检测又叫幅度解调&#xff0c;在许多领域都有重要的应用。如果载波信号是确定的&#xff0c;那么通常可以采用同步解调的方式&#xff0c;这种方式的信噪比最好&#xff0c;…

SQL Server 2005 DTS导入平面数据

SQL Server 2005 DTS导入平面数据源时&#xff0c;总是被截断&#xff0c;无法执行的错误解决方案 1 典型的错误信息如下&#xff1a; 消息 * 错误 0xc02020a1: 数据流任务: 数据转换失败。列“列 2”的数据转换返回状态值 4 和状态文本“文本被截断&#xff0c;或者一个或多个…

python交换数组中的两个元素_[Python]华为面试题,交换两个数组的元素使之总和的差值最小。...

看看写了个 &#xff0c;实现不需数组长度一致&#xff0c;复杂度O(n^2),求好的算法/** arr1{1,2,3};* arr2{22,33,44,55};* 交换两个矩阵数据*/public void exchange(){int index0;int lenarr1.length;int currMinusgetMinus();while(true){for (int i 0; i < arr2.length…

c语言switch为什么要加break,c语言学习笔记 switch case语句为什么要加break

先来看一个没有break的例子&#xff1a;int main(){int a 1;switch (a){case 1:printf("1");case 2:printf("2");}}我们看一下它的汇编代码&#xff1a;switch (a)0137181F mov eax,dword ptr [a]01371822 mov dword ptr [ebp-0D0h],eax01371828 cmp dwor…

VC中ADO连接SQLSERVER的几种标准方式?

VC用ADO访问数据库全攻略,介绍了VC用ADO来访问数据库的各个对象及各方法&#xff0c;很经典&#xff0c;也很实用&#xff0c;很值得一看。 正文 一、ADO概述 ADO是Microsoft为最新和最强大的数据访问范例 OLE DB 而设计的&#xff0c;是一个便于使用的应用程序层接口。ADO 使您…

usb转ttl_[开源]双TYPEC转TTL串口模块

在工作中经常会用到USB转TTL串口调试工具。网上买的用的不顺手&#xff0c;所以做了一个。最终效果:渲染图实物图学习目的做一个USB转串口模块&#xff0c;使用学习渲染软件keyshot使用到的工具:立创EDA&#xff0c;keyshot等电烙铁&#xff0c;万用表等1.需要实现的功能4.根据…

linux smb 启动失败,[已解决]windows能看到smb,但是打不开

xiadao_81 于 2010-01-15 16:32:31发表:还是不行啊&#xff01;郁闷&#xff01;还会哪里原因的&#xff1f;我把配置中没有注释的全拿出来了74 workgroup mshome75 server string Samba Server76 guest okyes77 guest accountroot102 security share103 passdb backend td…

String类的构造与析构相关处理

String类原型&#xff1a; 1 Class String2 {3 Public:4 String(constchar*str);5 String(constString &other);6 ~String(void);7 String&operator(constString &other);8 Private:9 char*m_data;10 };String的析构函数 1 String::~String(void)2 {3 delete []m_d…

cocos2dx 字体外发光_在电致发光研发领域,选择有机材料是基于哪些原因?

阅读本文前&#xff0c;请您先点击上面的蓝色字体&#xff0c;再点击“关注”&#xff0c;这样您就可以免费收到最新内容了。每天都有分享&#xff0c;完全是免费订阅&#xff0c;请放心关注。声明&#xff1a;本文转载自网络&#xff0c;如有侵权&#xff0c;请在后台留言联系…

android点击下拉历史记录,uni-app,社交应用中,聊天页面下拉onPullDownRefresh获取历史消息,数据合并之后,滚动到下拉之前的位置,页面看不见闪动,完美解决...

一般下拉之后&#xff0c;拿到数据合并&#xff0c;会默认展示顶部第一条&#xff0c;模仿其他聊天应用&#xff0c;回到下拉之前位置&#xff0c;如果不做处理&#xff0c;可以看见下拉得到的数据&#xff0c;本方法完美解决有问题可以留言或者加qq445849201讨论&#xff0c;亲…

WebOS + WebIM

此已文重新编辑.WebOSWebOS 是基于web技术实现的类似于桌面操作系统交互风格的应用程序。实现WebOS的主要技术可以是JavaScript或者是RIA(Flex\SL)。在JS领域内的最强大和最著名的可能要数eyeos了。本文所述的WebOS也是采用JavaScript开发的。图1&#xff1a;此应用主要是用于大…

雨滴桌面rainmeter素材_win10 桌面如何做到清爽好看?这篇教程给你答案

当一个电脑用的时间长了以后&#xff0c;难免就会变得非常杂乱。伟大的领袖曾经说过&#xff0c;要像倒腾自己的发型一样折腾好自己的桌面。道理咱都懂&#xff0c;可是大家动起手来就傻眼了&#xff0c;这啥玩意啊&#xff0c;算了吧&#xff0c;还是不弄了。本着慈悲为怀&…

met40如何升级成鸿蒙系统,再见了,EMUI11!你好,华为鸿蒙!

本文原创&#xff0c;请勿抄袭和搬运&#xff0c;违者必究鸿蒙终于来了华为研发鸿蒙OS已经有四五年的时间&#xff0c;诞生时间比大家想象的还要早&#xff0c;并不是为了替代安卓和专门推出的鸿蒙。因为从一开始华为就确定鸿蒙OS是一款面向万物互联时代的操作系统。从华为面向…

学习委托

简单实例 1 publicclasstest2 {3 publicdeledate voidMenuHandler(stringusername);4 publicvoidMenuHandlershixian(stringusername)5 {6 response.write(username);7 }8 publicvoidshow()9 {10 MenuHandler mhMenuHandlershixian;11 mh("majuan");12 }13 publicsta…

ups容量计算和配置方法_UPS电路设计的空开、电缆及电池如何配置,计算依据是什么...

很多朋友问到关于ups相关的计算&#xff0c;其实关于ups方面的计算还是挺多&#xff0c;ups无论是接空开&#xff0c;还是连接电缆&#xff0c;以及选择电池&#xff0c;都可能需要计算它的电流或功率等&#xff0c;那么今天我们来详细了解下ups的相关计算。一、ups空开及电缆的…

android webdav客户端,WebDAV精灵(WebDAV客户端)

WebDAV精灵 让您的Phone,,Pad 成为WebDav客户端,能够使用从WebDav服务器下载文件和上载文件 .一些常用的WebDAV站点:https://webdav.yandex.com(http://www.yandex.com/)https://dav.box.com/dav(https://www.box.net/)https://webdav.mydrive.ch(https://mydrive.ch)http://my…