hive调优
一、fetch策略
hive.fetch.task.conversion
现在版本默认值是more
none:表示禁用,任何查询都会走mr(count好像不走)
minimal:select*,filter,limit以及分区表的分区字段查询不会走MR,其余的都会
more:全局查询,字段查询,limit,count,filter等都不会走MR
二、local.auto(本地模式)
hive.exec.mode.local.auto默认值是false
开启本地 mr
set hive.exec.mode.local.auto=true;
设置 local mr 的最大输入数据量,当输入数据量小于这个值时采用 local mr 的方式,默认 为 134217728,即 128M
set hive.exec.mode.local.auto.inputbytes.max=50000000;
设置 local mr 的最大输入文件个数,当输入文件个数小于这个值时采用 local mr 的方式,默 认为 4
set hive.exec.mode.local.auto.input.files.max=10;
三、严格模式
hive.mapred.mode默认值是strict
在该模式下,笛卡儿积(join没有on)、分区表扫描没有加分区字段、全表扫描和全表的order by没有加limit是不会被允许
set hive.mapred.mode=nonstrict;非严格模式以上操作是允许的
四、推测式执行
hive.mapred.reduce.tasks.speculative.execution默认值是true
解决的问题:
1.数据倾斜(不一定能解决)
2.某个task在某个节点执行时,该节点负载高,执行时间超过阈值,就会在其他节点并行执行该task
五、谓词下压
hive.optimize.ppd默认值时true
在SQL中,条件的业务逻辑尽可能的提前执行,减少后续待处理作业的数据量
ppd(PredicatePushDown)
六、合理设置 Reduce 数
要根据作业的复杂度、最终输出文件的大小进行调试
MR中,reducer个数决定了作业最终输出的文件数,如果没有reducer,则由mapper个数决定
1)调整 reduce 个数方法一
(1)每个 Reduce 处理的数据量默认是 256MB
hive.exec.reducers.bytes.per.reducer=256000000
(2)每个任务最大的 reduce 数,默认为 1009
hive.exec.reducers.max=1009
(3)计算 reducer 数的公式
N=min(参数 2,总输入数据量/参数 1)
2)调整 reduce 个数方法二 (多用这种方法)*****
在 hadoop 的 mapred-default.xml 文件中修改 或者在hive执行时修改
设置每个 job 的 Reduce 个数 set mapreduce.job.reduces = 5;
七、合并小文件
1)在 map 执行前合并小文件,减少 map 数:CombineHiveInputFormat 具有对小文件进行合
并的功能(系统默认的格式)。HiveInputFormat 没有对小文件合并功能。
set hive.input.format= org.apache.hadoop.hive.ql.io.CombineHiveInputFormat;
2)在 Map-Reduce 的任务结束时合并小文件的设置:
在 map-only 任务结束时合并小文件,默认 true
SET hive.merge.mapfiles = true;
在 map-reduce 任务结束时合并小文件,默认 false
SET hive.merge.mapredfiles = true;
合并文件的大小,默认 256M
SET hive.merge.size.per.task = 268435456;
当输出文件的平均大小小于该值时,启动一个独立的 map-reduce 任务进行文件 merge
SET hive.merge.smallfiles.avgsize = 16777216;
3)手动将hive表中的小文件合并(仅支持RC和ORC格式的数据)
alter table table_name concatenate;
八、并行执行
hive.exec.parallel默认值是false
通过设置参数 hive.exec.parallel 值为 true,就可以开启并发执行。
不过,在共享集群中,需要注意下,如果 job 中并行阶段增多,那么集群利用率就会增加。
set hive.exec.parallel=true; //打开任务并行执行
set hive.exec.parallel.thread.number=16; //同一个 sql 允许最大并行度,默认为 8。
当然,得是在系统资源比较空闲的时候才有优势,否则,没资源,并行也起不来。
九、数据倾斜
1.group by
Map 阶段同一 Key 数据分发给一个 reduce,当一个 key 数据过大时就倾斜了
1)开启 Map 端聚合参数设置
(1)是否在 Map 端进行聚合,默认为 True
set hive.map.aggr = true
(2)在 Map 端进行聚合操作的条目数目
set hive.groupby.mapaggr.checkinterval = 100000
(3)有数据倾斜的时候进行负载均衡(默认是 false)
set hive.groupby.skewindata = true
当选项设定为 true,生成的查询计划会有两个 MR Job。第一个 MR Job 中,Map 的输出
结果会随机分布到 Reduce 中,每个 Reduce 做部分聚合操作,并输出结果,这样处理的结果
是相同的 Group By Key 有可能被分发到不同的 Reduce 中,从而达到负载均衡的目的;第二
个 MR Job 再根据预处理的数据结果按照 Group By Key 分布到 Reduce 中(这个过程可以保证
相同的 Group By Key 被分布到同一个 Reduce 中),最后完成最终的聚合操作。
2. Count(Distinct) 去重统计
数据量小的时候无所谓,数据量大的情况下,由于 COUNT DISTINCT 操作需要用一个
Reduce Task 来完成,这一个 Reduce 需要处理的数据量太大,就会导致整个 Job 很难完成,
一般 COUNT DISTINCT 使用先 GROUP BY 再 COUNT 的方式替换,但是需要注意 group by 造成
的数据倾斜问题.
3.大表 join大表
我们首先找出来产生数据倾斜的字段,先将其他字段进行join操作,再union all ,将第一张表前面加一个随机数,第二张表直接扩容,再join,避免数据倾斜
参考:https://blog.csdn.net/qq_36039236/article/details/107696305