数据倾斜:
hive在跑数据时经常会出现数据倾斜的情况,使的作业经常reduce完成在99%后一直卡住,最后的1%花了几个小时都没跑完,这种情况就很可能是数据倾斜的原因,解决方法要根据具体情况来选择具体的方案
(1)key值发生倾斜,key值包含很多空值或异常值
赋一个随机值来分散key,如果不需要也可以过滤掉或不适用该key
select case when userid is null then cast ( rand ( 47 )* 100000 as i nt ) else userid end
(2)不同数据类型关联产生数据倾斜
场景:用户表中user_id字段为int,log表中user_id字段既有string类型也有int类型。当按照user_id进行两个表的Join操作时,默认的Hash操作会按int型的id来进行分配,这样会导致所有string类型id的记录都分配到一个Reducer中。
解决方法:把数字类型转换成字符串类型
select * from users a
left outer join logs b
on a.usr_id = cast(b.user_id as string)
(3)join 倾斜优化:在map端进行join
- set hive.auto.convert.join.noconditionaltask = true;
- set hive.auto.convert.join.noconditionaltask.size = 10000000;
- set hive.auto.convert.join=true;
- set hive.mapjoin.smalltable.filesize=25M;
- set hive.optimize.skewjoin.compiletime=true ---如果是大表和大表join
set hive.optimize.skewjoin=true;
set hive.skewjoin.key=100000;
hive.optimize.skewjoin.compiletime和hive.optimize.skewjoin区别为前者为编译时参数,后者为运行时参数。
skewjoin原理:
-
对于skewjoin.key,在执行job时,将它们存入临时的HDFS目录。其它数据正常执行
-
对倾斜数据开启map join操作,对非倾斜值采取普通join操作
-
将倾斜数据集和非倾斜数据及进行合并操作
开启skewed key 可以在建表时指定skewed key
create table xxx (key string,value string) skewed by(key);
(4)小表与大表关联
通过mapjoin优化
set
hive.auto.
convert
.
join
=
true
; //将小表刷入内存中
set
hive.mapjoin.smalltable.filesize = 2500000 ;//刷入内存表的大小(字节)
(5)group by 倾斜优化
改变写法或参数设置
可以将倾斜的数据单独拿出来处理。最后union回去
参数设置:
set hive.map.aggr=true --相当于combinner
hive.groupby.mapaggr.checkinterval = 100000
hive.map.aggr.hash.min.reduction=0.5
--预先去100000条数据聚合,如果聚合后的条数/100000>0.5,则不在聚合
set hive.groupby.skewindata=true;
(6)不可拆分大文件引发数据倾斜
例如:GZip
可以使用bzip2或zip等支持文件分割的压缩算法
(7)多维聚合引发的数据膨胀
例如:rollup
在Hive中可以通过参数 hive.new.job.grouping.set.cardinality 配置自动控制作业拆解。如果最后拆解的键组合大于默认值30,会启动新的任务处理该值之外的组合。
参考:https://blog.csdn.net/s646575997/article/details/51510661