问题:
使用sql语句,insert into xxx select * from xxx group by;等复杂的逻辑语句
出现reducer数量超过1000000
原因分析:
Hadoop MapReduce程序中,reducer个数的设定极大影响执行效率 ,这使得Hive怎样决定reducer个数成为一个关键问题。遗憾的是Hive的 估计机制很弱,
猜测星环在处理reducer的时候是根据map数决定的,如果数据出现倾斜,会产生很多reducer
reducer的数量与输出文件的数量有关,如果reducer数太多,会产生大量小文件,对HDFS造成压力.如果redcuer数量太少,每个reducer要处理很多数据,容易拖慢运行时间或者造成OOM.
说明:
也有些情况是固定只有一个reduce的(不管有没指定reduce数量):
a.没有group by的汇总
b.使用order by全局排序
c.笛卡尔积
d.count(distinct)
但这几种情况一般是我们需要避免的,因为会造成性能瓶颈.
解决:
SET mapred.reduce.tasks = 800;
原理:
如果 reducer 数量过多,一个 reducer 会产生一个结数量果文件,这样就会生成很多小文件,那么如果这些结果文件会作为下一个 job 的输入,则会出现小文件需要进行合并的问题,而且启动和初始化 reducer 需要耗费和资源。
如果 reducer 数量过少,这样一个 reducer 就需要处理大量的数据,并且还有可能会出现数据倾斜的问题,使得整个查询耗时长。默认情况下,hive 分配的 reducer 个数由下列参数决定:
-
参数1:
hive.exec.reducers.bytes.per.reducer
(默认1G) -
参数2:
hive.exec.reducers.max
(默认为999)
reducer的计算公式为:
N = min(参数2, 总输入数据量/参数1)
可以通过改变上述两个参数的值来控制reducer的数量。也可以通过
set mapred.map.tasks=10;
直接控制reducer个数,如果设置了该参数,上面两个参数就会忽略。
可以参考这个:https://www.cnblogs.com/pengpenghuhu/p/11735422.html