HIVE-SQL-小文件优化
当文件数目过多时,会给HDFS带来压力,进而影响namenode查找文件路径的压力,可以通过合并Map和Reduce的输出文件来减少文件数。
为了减少文件数目,可能通过合并小文件的方法来实现,具体措施如下:
#map执行前合并小文件
如果输入文件过小的时候,放置大量的maptask也不划算
1.在map执行前合并小文件,减少map数:CombineHiveInputFormat具有对小文件进行合并的功能(系统默认的格式)。HiveInputFormat没有对小文件合并功能
set hive.input.format= org.apache.hadoop.hive.ql.io.CombineHiveInputFormat;
#Map-Reduce的任务结束时合并小文件
##map-only任务结束时合并小文件
在map-only任务结束时合并小文件,默认true
SET hive.merge.mapfiles = true;
此参数设置为true的时候,仅合并mapreduce作业的map only作业。
如以下 SQL 有 50 个 mapper,没有 reducer。每个 mapper 仅仅输出百分之一的数据。结果输出了 50 个小文件。如果 hive.merge.mapfiles=true,会再启动一个作业来合并文件。
set hive.execution.engine=mr;
insert overwrite table t2 select * from t1 where hash(c1) % 100 = 1;
##在map-reduce任务结束时合并小文件
在map-reduce任务结束时合并小文件,默认false
SET hive.merge.mapredfiles = true;
此参数设置为 true 的时候,仅合并 有 reduce 任务的 mapreduce 作业。
如以下 SQL 有 50 个 mapper,有 40 个 reducer。每个mapper仅仅输出百分之一的数据。结果 reduce 任务输出了40个小文件。如果 hive.merge.mapredfiles=true,会再启动一个作业来合并文件。
set hive.execution.engine=mr;
insert overwrite table t2 select c1 from t1 where hash(c1) % 100 =1 group by c1 ;
#小文件的判断
如果一个 job 结束后,生成的文件的平均大小小于参数 hive.merge.smallfiles.avgsize 设定的值,则认为是小文件。如以下设置平均小文件的大小为 128M。
set hive.merge.smallfiles.avgsize=128000000;
合并后的目标文件大小
希望的合并后的目标文件大小,如果此值小于 hive.merge.smallfiles.avgsize, 则此值为 hive.merge.smallfiles.avgsize,默认256M
set hive.merge.size.per.task=128000000;
#总结
上面几个参数配合使用才能使小文件合并设置生效