1.使用Explain命令,查看执行计划,不会真正的执行,可以详细的查看sql执行的每一个细节。
2.fetch指的是hive在对某些情况下可以不是用mapreduce,在配置文件中修改hive.fetch.task.conversion,在属性修改为more以后全局查找,字段查找,limit等都不走mapreduce。
3.大多数的hadoopjob需要hadoop完整的性能,对于一些数据量非常小的hive任务,触发查询执行计划的时间比实际执行job消耗的时间还多。Hive可以通过本地模式在单台机器上处理所有的任务,处理小的数据集,时间被明显缩短。设置hive.exec.mmode.local.auto为true。
- 表的优化:
1.小表join大表
- 小表Join大表,设置选择mapjoin set hive.auto.convert.join=true;
- 设置大表小表的阈值,set hive.mapjoin.smalltable.filesize=2500000;
- 这样两个表在Join的时候会先mapjoin小表。
- 大表join大表
按空key进行过滤:
有时表的数据很大,key对应的数据太多,而相同的key会发送到相同的reduce上,从而导致内存不够。我们需要对key进行分析,大多是异常数据。例如key对应的字段为空。
空key过滤使用场景:
- 非inner join
- 不需要字段为Null的
先join再过滤 ,先过滤再join(效率高)
空key的转换:
有时空key是正常的数据,而且我们需要这种数据,此时我们可以对表中key的字段赋随机值,使得数据分布在不同的reduce中。
例子:
不进行随机:
insert overwrite table jointable
select n.* from nullidtable n left join bigtable b on n.id = b.id;
进行随机:
insert overwrite table jointable
select n.* from nullidtable n full join bigtable o on nvl(n.id,rand()) = o.id;
3.分桶表 SMB(Sort Merge Bucket join)
创建分桶表,按id进行分桶,提高了并发,到最后再把分桶的结果进行合并,能极大的提高速度。
5.group by
默认情况下map阶段同一个key发送的一个reduce,当key的数据过多时就造成了数据倾斜。这种情况下不是的所有的聚合都在reduce完成,也可以在map端进行部分聚合,在reduce端在合并。
- 开启Map端参数合并
- Setv hive.map.aggr=true
- 设置聚合的条数
set hive.groupby.mapaggr.checkinterval=10000
- 有数据倾斜时进行负载均衡
Set hive.groupby.skewindata=true
在设置为true的时候生成的查询计划会有两个mrjob,第一个按key reduce进行预聚合,第二个在根据key进行合并完成聚合。
6.Count(distinct)去重统计
慎用distinct,无论设置多少个reduce结果都会放在一个reduce,数据太大,会造成oom。这种情况可以使用group by代替,再把结果作为子表,再次查询去重,但是要注意groupby造成的数据倾斜的问题。
- 笛卡尔积
在没有关联条件或者关联条件无效的on时,hive只能用一个reduce来完成笛卡尔积。
- 行列过滤
列处理:
在查询的时候,只拿到所需要的列,有分区用分区,少用select*
行处理:
在分区剪裁中,当使用外关联时,如果将副表的过滤条件写在 Where 后面,那么就会先全表关联,之后再过滤。
分为先关联再过滤,先过滤在关联(效果会调高)。
- 创建分区,和分桶表
- 合理设置map和reduce的数量。
- 复杂文件增减map数
增加 map 的方法为:根据
computeSliteSize(Math.max(minSize,Math.min(maxSize,blocksize)))=blocksize=128M 公式, 调整 maxSize 最大值。让maxSize 最大值低于 blocksize 就可以增加 map 的个数。
13.小文件进行合并
在map执行前提前合并小文件,减少map数:combinehiveinputformat具有合并小文件的功能,(系统默认的格式),hiveinputformat没有这功能。
可以在mapreduce结束时合并小文件。
在map-only任务结束时合并小文件的设置:默认true
Set hive.merge.mapfiles=true
在Map-reduce任务结束时合并小文件默认false
Set hive.merge.mapfiles=true
合并文件的大小默认是256m
Set hive.meger.size.per.task=268435456;
当输出文件的平均大小小于该值时,启动一个独立的mapreduce任务进行文件merger
Set hive.meger.smallfiles.avgsize=16777216
- 合理设置reduce数
- 调整reduce个数方法一
每个reduce处理的数据量默认是256m
Hive.exex.reduces.bytes.per.reducer=256m
每个任务最大的reduce数,默认为1009
Hive.exex.reduces.max=1009
计算公式
N=min(参数2,总输入量数/参数1)
- 调整reduce个数方法二。
在hadoop的mapred.xml文件中修改
设置每个job的reduc个数
Set mapreduce.job.reduces=15
- 设置并行执行
- 严格模式
Hive可以通过设置防止一些危险的操作。
- 分区表不使用分区过滤。
- 使用orderby 没有limit过滤
- 笛卡尔积
- jvm重用
Jvm的重用一般设置参数为10-20中间,jvm适合处理小的任务,因为启动执行计划的时间可能要大于执行job的时间,开始可以减少时间,如果是大的数据使用jvm重用会造成oom。
17.压缩