文档章节

Lucene与HBase的组合使用及HBasene的分析报告

Poorzerg
 Poorzerg
发布于 2014/02/08 14:51
字数 2030
阅读 1.5K
收藏 2

Lucene简介

  Lucene中,以document的形式作为搜索的主体。document由fieldName和fieldValue所组成,每个fieldValue又可以由一个或多个term元素来组成。基于不同的分词及索引规则,可用于搜索fieldValue的term少于组成fieldValue的term。Lucene的搜索基于反向索引,包含着可用于搜索document的field信息。通过Lucene,可以正向查找document,以便了解其包含哪些field信息;也可以通过反向索引,通过搜索字段的term,来查询包含该term的document。

 

[ 图1 ]  Lucene总体架构

 

  由图1所示,IndexSearcher实现了搜索的逻辑,IndexWriter实现了文档的插入与反向索引的建立,IndexReader由IndexSearcher调用以便读取索引的内容。IndexReader和IndexWriter都依赖于抽象类Directory,Directory提供操作索引数据及的API。

  标准的Lucene是基于文件系统和基于内存的。

  标准基于文件系统的后端的缺点在于,随着索引增加性能会下降,人们使用了各种不同的技术来解决这个问题,包括负载均衡和索引分片(index sharding,在多个Lucene实例之间切分索引)。尽管分片功能很强大,但它让总体的实现架构变得更复杂,并且需要大量对期望文档的预测知识,才能对Lucene索引进行合适地分片。另一方面,在大数据量的情况下,segment的合并花销巨大;频繁的update数据将使得Lucene对Disk io产生巨大的影响。一个新的数据的update,可能导致一部分根本没有变化的索引被重写很多次,并且可能导致很多的小的index segment,造成了search的性能下降。

  Lucene的优势在于索引查找的迅速,而非document的存储。为解决上述问题,基于NoSQL数据库存储索引的后端结构应运而生。

 

以下,将基于HBase的实现来进行分析。

实现方法

  在Lucene中,其会操作两个单独的数据集:

  • 文档数据集中存储了所有文档,包括存储的字段等。

  • 索引数据集中存储了所有字段/词汇/词频/位置等信息,以及包含当前字段的document

 

  如果要实现将Lucene的后端移植到HBase上,直接构建一个Directory的实现并不会是最简单的。在已有的开源项目中,Lucandra和HBasene均采用了直接重写IndexReader和IndexWriter的方式,直接绕开了Directory的API。此实现并不会重写Lucene的索引查询机制。如若重载IndexSearcher,则可以在使用现有的Lucene索引查询机制上,根据后端的功能增强性能。

 

[ 图2 ] Lucene的后端重新设计

 

  图2的设计,可以将Lucene后端与HBase整合起来,将索引数据存储到HBase中,从而利用HBase的大数据存储以及分布式性能。

 

架构设计

  在架构设计上,将HBase用作索引的持久化后端,同时可以如网上所说,基于内存实现一套缓存机制,用来提高数据读取速度。实现一套高效的缓存同步机制,也将有利于数据读写速率的提高。

 

 

[ 图3 ] 带有内存缓存以及同步缓存的HBase后端实现

 

  对于HBase的访问,每一次交互都需要通过以太网,以太网的运行状态将大大影响系统的使用情况,而索引的建立又希望能达到实时且高响应。为了平衡这两种相互冲突的需求,在内存中,缓存能够最小化HBase用于搜索和文件返回的数据读取量,从而极大提升性能;按照需要运行为多个Lucene示例以支持日益增长的搜索客户端的能力。后者需要最小化缓存的生命周期,从而和HBase实例(上面提到实例的副本)中的内容同步。通过为活动参数实现可配置的缓存时间,限制每个Lucene实例中展现的缓存,我们可以达成一种折中方案。

  根据上述所描述的结构,对于读操作,首先会检查所需数据是否在内存中且没有过期,如果有效将直接使用,否者将从HBase中获取数据并更新到内存中。而对于写操作,可以简化到直接将数据写入到HBase中,进而不需要考虑是否需要建立或更新缓存这种复杂的问题,这也将提高系统的实时响应性。

 

HBase Table的实现

当前了解到的两种可参考的实现方式:HBasene类型、Lucandra类型。

 

1-- HBasene

其索引表由以下几个column family组成:

  • fm.sequence:记录sequenceId,表示当前添加的第几个document。在执行createLuceneIndexTable时创建该行,且rowKey为segmentId,Column.qulifier为qual.sequence,Column.value=-1。每add一个document,当前segmentId的Column.value将自增1。

  • fm.doc2int:每个document的存储都将被分配一个唯一的id,如果document的Field.Store=YES,则能够通过该id获取到对应的document的全部信息。

  • fm.fields:记录了Field中value的内容,rowKey为documentId,Column.qulifier为FieldName,Column.value为FieldValue的内容。

  • fm.termVector:向量偏移数据,用于模糊查找,记录了偏移量等信息,rowKey为FileldName/Term的组合,Column.qulifier为documentId,Column.value为指向的document中的所有位置偏移量。Column.value的结构为:[A][size][position]……[position]

  • fm.termFrequencies:关键词在每个document中出现的频率,rowKey结构为zfm/FileName/Term,Column.qulifier为documentId,Column.value为出现的次数。

 

2-- Lucandra

在Lucendra中,只有两个ColummFamily来存储数据,分别是TermInfo和Documents

<Keyspace Name="Lucandra"> 
    <ColumnFamily   Name="TermInfo" CompareWith="BytesType" ColumnType="Super"  CompareSubcolumnsWith="BytesType"  KeysCached="10%" /> 
    <ColumnFamily Name="Documents" CompareWith="BytesType" KeysCached="10%" /> 
</Keyspace>

 

  • TermInfo

        TermInfo存储了Lucandra逆向索引的信息,用来存储index的Field信息,其结构如下:

        RowKey:field/term

        SuperColumn.name:documentId

        [ SubColumn.name:"frequencies"  Column.value:count ]

        [ SubColumn.name:"position"  Column.value:position vector ]

        [ SubColumn.name:"offsets"  Column.value:offsets vector ]

        [ SubColumn.name:"norms"  Column.value:norms vector ]

 

由于HBase中不存在SuperColumn和SubColumn的概念,我们可以将其简化为:

        RowKey:field/term

        Column.qulifier:documentId

        Column.value:fieldInfo [ 此fieldInfo可以通过AVRO类定义 ]

 

  • Documents

        Documents存储了Document数据,其结构如下:

        RowKey:documentId

        Column.name:fieldName

        Column.value:fieldValue

 

对比:

        由HBasene的表结构可以知道,对于每一个document的更新以及每一次term的查询,都需要操纵多行数据才能实现,逻辑上相对复杂;而Lucandra只需要处理两行(documents及TermInfo各一行)。但是HBasene的优势在于单行的存储结构小,每次与HBase交互只需要传输少量的数据及可,并且不像Lucandra结构一样需要而外的AVRO组件来序列化与反序列化数据。

 

HBasene的缺陷:

        1、HBasene在三年前已经停止了其项目的更新,开源的支持断开了。

        2、在对HBasene的最新源码分析过程中,首先是发现其设计上保留着segment的概念,但是其设计阻碍着document的查询。其documentId由segmentId/sequenceId组成,每次segment的commit,sequenceId恢复为-1。而search时返回的TopDocs中只包含了sequenceId[int]。

        3、每次添加document时,只有fm.Fields以及fm.doc2int的数据被实时flush到了HBase中,而其他数据需要segment大小到了一定程度[默认1000条document]才commit,容易造成数据缺失。在segment没被commit的情况下,是无法查询到新添加的document的。

        4、HBase Table的设计中,没有考虑到当document中fieldName相同的情况。当fieldName相同的情况下,后面添加的会覆盖前面添加数据的,最后只保留最后添加的一份。

        5、fm.termVector中,Column.value保存的并不是positionVector信息,而是segment中所有document里出现的次数。

        6、fm.termFrequencies只是单纯地存储了,并没有被应用上。

        7、IndexWriter的重写并没有实现所有函数,只实现了最基本的addDocument

        8、对IndexSearch的重写和扩展也不够。


© 著作权归作者所有

下一篇: Maven系列--序
Poorzerg
粉丝 12
博文 21
码字总数 23485
作品 0
深圳
程序员
私信 提问
HBase技术双周刊第1期:HBase 在人工智能场景的使用

精彩直播 HBase多模式 HBase多模式,包括 分析层:支持复杂分析、算子下推;多模式层:提供各种模型转换,贴切业务;索引引擎:提供索引支持,基于 Lucene ;存储引擎:提供 KV 支持,基于L...

萌萌怪兽
2018/11/22
0
0
HBase+Spark技术双周刊第1期

精彩直播 HBase多模式 HBase多模式,包括 分析层:支持复杂分析、算子下推;多模式层:提供各种模型转换,贴切业务;索引引擎:提供索引支持,基于 Lucene ;存储引擎:提供 KV 支持,基于L...

hbase小能手
2018/11/23
0
0
HBase2.0商用首发--有哪些值得期待的新特性

【HBase生态+Spark社区大群】 1.技术交流钉钉大群【强烈推荐!】 群内每周进行群直播技术分享及问答 加入方式1: 点击链接申请加入 https://dwz.cn/Fvqv066s 加入方式2: 钉钉扫码加入: 2....

HBase技术社区
2018/12/04
0
0
选择阿里云数据库HBase版十大理由

根据Gartner的预计,全球非关系型数据库(NoSQL)在2020~2022预计保持在30%左右高速增长,远高于数据库整体市场。 阿里云数据库HBase版也是踏着技术发展的节奏,伴随着NoSQL和大数据技术的兴...

阿里云云栖社区
2019/04/24
0
0
为了实现在线库的复杂查询,你还在双写吗?

一、在线库不支持在线复杂查询 做在线业务的开发者经常会碰到这样的难题:在线数据库上面运行稍微复杂点的查询,在线业务就挂了!不管是单机数据库如MySQL、PG,还是分布式数据库,HBase、M...

阿里云云栖社区
2019/11/19
0
0

没有更多内容

加载失败,请刷新页面

加载更多

spring-boot-maven-plugin not found的解决方案。

通过IDE创建一个springboot项目, <plugin> <groupId>org.springframework.boot</groupId>//这行红色 <artifactId>spring-boot-maven-plugin</artifactId>//这行红色</plugin> 提示sprin......

一片云里的天空
今天
52
0
OSChina 周三乱弹 —— 我可能是个憨憨

Osc乱弹歌单(2020)请戳(这里) 【今日歌曲】 @宇辰OSC :分享Hare Je的单曲《Alan Walker-Faded(Hare Je remix)》: #今日歌曲推荐# 可以放松大脑的一首纯音乐 《Alan Walker-Faded(Har...

小小编辑
今天
99
0
搞定SpringBoot多数据源(3):参数化变更源

春节将至,今天放假了,在此祝小伙伴们新春大吉,身体健康,思路清晰,永远无BUG! 一句话概括:参数化变更源意思是根据参数动态添加数据源以及切换数据源,解决不确定数据源的问题。 1. 引言...

mason技术记录
昨天
99
0
sql 基础知识

sql 基础知识 不要极至最求一条sql语句搞定一切,可合理拆分为多条语句 1. sql 变量定义与赋值 Sql 语句中,直接在SELECT使用@定义一个变量,如:[@a](https://my.oschina.net/a8856225a)。 ...

DrChenXX
昨天
57
0
MacOSX 安装 TensorFlow

TensorFlow是一个端到端开源机器学习平台。它拥有一个包含各种工具、库和社区资源的全面灵活生态系统,可以让研究人员推动机器学习领域的先进技术的。 准备 安装 Anaconda TensorFlow 安装的...

叉叉敌
昨天
79
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部