HIVE TopN shuffle 原理

本文介绍了HIVE在处理TopN问题时的一个优化策略,即通过将带有limit算子的order by推至map端,减少数据shuffle。详细解析了ReduceSinkOperator如何利用TopNHash来决定数据是否进入topN堆,以及在遇到group by limit时的处理方式。同时,提到了窗口函数如Rank的map端优化,并探讨了在数据无序和有序情况下map端topN的实现和效果。
摘要由CSDN通过智能技术生成

作者:

辛现银,花名辛庸,阿里巴巴计算平台事业部 EMR 技术专家。Apache Hadoop,Apache Spark contributor。对 Hadoop、Spark、Hive、Druid 等大数据组件有深入研究。目前从事大数据云化相关工作,专注于计算引擎、存储结构、数据库事务等内容。

HIVE TopN Shuffle

TopN 问题是排序中的一个经典问题。对于一个长度为 m 的数组,取其最大的 n (n <= m) 条数据,可以不必对整个数组进行全排。一般的算法对 m 进行全排的复杂度大约为 mlog2(m)。假设我们只取其中最大的 n 条,那么可以把这个复杂度降低到 m * log2(n)。如果 n << m,那么收益还是很大的。

HIVE-3562 引入了一个针对 TopN 的优化,即将带有 limit 算子的 order by 推至 map 端,这样 map 不必将所有数据 shuffle 到 reduce。order by 和 limit 算子在日常使用场景中经常一起出现,因此这个优化就显得很有必要。

抛开 limit 是如何下推的不管,我们这里只关注 ReduceSinkOperator 拿到 limit 算子后如何处理这个逻辑。代码入口是 ReduceSinkOperator#process(...) 方法。

ReduceSinkOperator 内维护了一个 TopNHash 变量 reducerHash,该变量决定了一条 row 是否被 collect,也就是说,是否被 shuffle 到下游:

// Try to store the first key.
// if TopNHashes aren't active, always forward
// if TopNHashes are active, proceed if not already excluded (i.e order by limit)
      final int firstIndex =
          (reducerHash != null) ? reducerHash.tryStoreKey(firstKey, partKeyNull) : TopNHash.FORWARD;
if (firstIndex == TopNHash.EXCLUDE)
       {
return; // Nothing to do.
      }
// Compute value and hashcode - we'd either store or forward them.
      BytesWritable value = makeValueWritable(row);


if (firstIndex == TopNHash.FORWARD) {
        collect(firstKey, value);
      } else {
// invariant: reducerHash != null
        assert firstIndex >= 0;
        reducerHash.storeValue(firstIndex, firstKey.hashCode(), value, false);

其中有一个非常重要的方法TopNHash.tryStoreKey(...)。它的意思是尝试把该行存到一个 topN 的 heap 中。之所以是尝试,是因为它有几个返回值

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值