当前位置: 代码迷 >> 综合 >> hive.groupby.skewindata及数据倾斜优化
  详细解决方案

hive.groupby.skewindata及数据倾斜优化

热度:77   发布时间:2023-12-08 22:14:20.0

一、hive.groupby.skewindata

set hive.groupby.skewindata=true;

数据倾斜时负载均衡,当选项设定为true,生成的查询计划会有两个MRJob。第一个MRJob 中,Map的输出结果集合会随机分布到Reduce中,每个Reduce做部分聚合操作,并输出结果,这样处理的结果是相同的GroupBy Key有可能被分发到不同的Reduce中,从而达到负载均衡的目的;第二个MRJob再根据预处理的数据结果按照GroupBy Key分布到Reduce中(这个过程可以保证相同的GroupBy Key被分布到同一个Reduce中),最后完成最终的聚合操作。

在这里插入图片描述

由上图下部分过程可看到过程,由此带出解决数据倾斜的方式。

二、关于数据倾斜出现原因:

  • 对于join过程来说,如果出项较多的key值为空或异常的记录,或key值分布不均匀,就容易出现数据倾斜。
  • 对于group by 过程来说,如果某一个key值有特别的多的记录,其它key值的记录比较少,也容易出项数据倾斜。

Join实现原理举例:

select name, orderidf
from user t1
join order t2 on t1.uid=t2.uid

Group by实现原理举例

sql = select rank, isonline, count(1)
from city
group by 1, 2

三、数据倾斜的解决方案

①、join引起数据倾斜的解决方法

  • 如果是由于key值为空或为异常记录,且这些记录不能被过滤掉的情况下,可以考虑给key赋一个随机值,将这些值分散到不同的reduce进行处理。
  • 如果是一个大表和一个小表join的话,可以考虑使用mapjoin来避免数据倾斜。
    mapjoin原理可参考前一篇文章:浅谈Hive中Map Join原理及场景

②、group by 引起数据倾斜的解决方法

set hive.map.aggr=true

在map中会做部分聚集操作,效率更高但需要更多的内存。开启map之后使用combiner,这样基本上是对各记录比较同质的数据效果比较好,相反,则没有什么意义。通用的做法是设置下面两个参数:

set hive.groupby.mapaggr.checkinterval = 100000 (默认)执行聚合的条数
set hive.map.aggr.hash.min.reduction=0.5(默认)
#如果hash表的容量与输入行数之比超过这个数,那么map端的hash聚合将被关闭,默认是0.5,
#设置为1可以保证hash聚合永不被关闭;

在这里插入图片描述

还有一个方式是本文提及的set hive.groupby.skewindata=true

ps: 有博文反应该参数与set hive.map.aggr=true同时使用时候对distinct结果会有影响,但我实测并没有,可能是特定情况才会出现?如若碰到还请随时交流。hive.groupby.skewindata 和 hive.map.aggr 组合的坑

参考:

hive数据倾斜原理与解决方案

hive原理与源码分析


学习交流,有任何问题还请随时评论指出交流。

  相关解决方案