中总结并经过自己一些测试后得出,可能也存在错误,欢迎各位借鉴或指出;
大佬在文章中的已经论述的很详细,且有例子指出,这里我就不一一重复了;
1、Map
a、对于map的个数控制主要有4个参数,分别是
set mapred.max.split.size; -- 每个Map最大输入大小
set mapred.min.split.size; -- 每个Map最小输入大小
set mapred.min.split.size.per.rack; -- 每个机架处理的最小slit
set mapred.min.split.size.per.node; -- 每个节点处理的最小split
b、设置参数值的时候,参数值大小必须按照下面规则设置;
set mapred.max.split.size >= set mapred.min.split.size >= set mapred.min.split.size.per.rack >= set mapred.min.split.size.per.node
很好理解,一个节点的输入数据量一定是要小于机架的,同理每个Map最小输入大小也要小于每个Map最大输入大小;但是大佬总结的et mapred.min.split.size一定要大于等于set mapred.min.split.size.per.rack,经过我测试,是否定的,min.split.size可以小于size.per.rack,但是size.per.rack一定得大于max.split.size!
c、然而四个参数,起作用的时候是有优先级的:
set mapred.max.split.size <= set mapred.min.split.size <= set mapred.min.split.size.per.rack <= set mapred.min.split.size.per.node
由此可见,我们大部分时候只要修改per.node即可,只是有时候超出了max.split.size,要根据情况加大该值即可;
但是根据大佬文章测试,mapper的修改还得根据处理的文件是否压缩,且压缩算法是否支持文件的切分;
有些是不支持切分的,大佬测试这时候可以调节set mapred.max.split.size参数,因为hive默认map前进行小文件合并,是合并了map吗?这个待验证;
2、Reduce
reduce调优相对简单一些
主要是两个参数和一个计算公式:
set hive.exec.reducers.bytes.per.reducer;-- 每个reduce的数据量大小(单位Byte),推荐调节这个参数即可控制
set mapred.reduce.tasks=100; -- 这是最简单粗暴的方式,不推荐因为可能会导致有的reduce节点数据量过大,导致内存溢出;
reduce计算方式:
Num=min(hive.exec.reducers.max,map输出数据量/hive.exec.reducers.bytes.per.reducer)
值得说的是,有些情况下只会产生一个reduce:
1、笛卡尔积;2、order by; 3、distinct;
因为他们是要进行全局数据的操作,只能将数据汇总到一个reduce进行聚合;