基于hadoop创建lucene索引(二)编程模型二

针对上篇提到的问题,我们采用一个新的编程模型来提高程序执行效率。在上篇所述的编程模型里,lucene创建索引的大部分开销集中在了reduce端,受限于reduce个数(因业务需要reduce个数不能随意增加),且索引合并过程完全依赖于磁盘读写速度。由此可找到两个突破口:

1.把大部分开销转移到map端,提高并发度。map个数主要取决于集群的规模,集群规模越大,可并发执行的map数越多。这样程序执行速度就取决于集群的规模,有较好的水平扩展性。Lucene建索引的三个主要步骤——原始文档转换、文本分析、保存至索引,均考虑在map端进行。

2.内存读写速度远远大于磁盘。当索引文件大小内存能承受时,可考虑直接基于lucene内存索引RAMDirectory创建索引,以提高索引速度。但对于我们的数据量而言,直接使用lucene内存索引是不可行的。这里使用归并的思想,把大数据拆成小数据,分而治之,内存中放不下时再在磁盘上进行合并。由于map的输入大小可以精确控制,所以可以保证map端基于内存建索引的过程不会出现OOM问题。

综上所述,可以得到一个改进的编程模型:先在map端基于内存建索引,输出已建好的索引块;然后在reduce端进行合并,由于reduce端需要处理的索引文件较大,所以这一步基于磁盘进行。

如果仅仅支持全量索引,只有add操作,这个模型已经能够满足我们的需求。其示意图如下:

索引更新难免有update操作和delete操作,上述模型不能直接满足需求。对lucene来说,update操作本质上是add+delete,只要解决了文档的删除问题,就可以满足各种索引更新需求。如何找到原文档所在的reduce节点位置呢?如果建索引的时候reduce分布有规律,根据文档数据的业务ID做了hash,重写过getPartition()方法,只需把删除指令传递给它所在的reduce;否则需要把delete广播给所有的reduce节点。

在我们的系统中,使用同样的硬件资源,这种模型后比上篇所述模型整整快了5倍,创建索引时间由15小时缩短到3小时。这种模型扩展性大大提升,只要集群规模足够大,map的时间可以继续缩短,索引创建时间基本上就是reduce合并索引所需的时间。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值