hive优化【增加执行的map数,reduce数】

hive中的启动的map数据量,以及reduce的数据量,都是由系统给控制的,一般来说,map的数据量是由文件的个数,以及文件量的大小所决定。如果你的文件很多,那么每个文件必然会启动一个map进行处理,或者你的文件非常大,是hdfs中block_size的N倍,那么就会分成N个文件,同样会启动N个map进行处理。而reduce的数据量则是根据你的key多少来决定的,一旦你的map生成的key非常多,那么reduce 的数据量也会比较多,最好避免像order by之类的全局统计参数,因为这类函数通常会只用一个reduce进行处理。

map多和少,reduce多和少的时间差异是很明显的,3个map和30个map的时间差异基本上就是10倍,这就是为什么我们竭尽全力的增加map数,而为了达到这个增加map数的目的,通常有两种途径,一种是尽量增加文件的大小,变成block_size 的N倍,还有一种办法是将大文件拆分为小文件,每个小文件进行处理的时候,都会启动一个map。前者的写法通常如下: create table cajeep_test2 as selecta.*,dummy_string(200) dummy_string from tdl_en_pp_node_stream_tmp2,通过增加的dummy_string的垃圾字段来增加数据文件的大小,从而实现将文件分成多个文件的作用;后者则需要set mapred.reduce.tasks = 30;set hive.merge.mapredfiles=false;,通过这两个设置,让系统每次启动reduce,都会启动30个,同时将reduce生成的文件不进行合并。因为每个reduce都会生成一个文件,光设置还不够,还需要让sql产生reduce的过程,而且是不能全局性的reduce(order by之类的),除非有group by之类能够保证产生多个reduce的代码之外,通常的代码后面都需要加上distribute by rand(123),让其自动产生一个reduce的过程,一旦产生reduce的过程,就会自动调用30个reduce,从而达到生成30个文件的目的。

具体的研究可以看下这篇文章:http://hugh-wangp.iteye.com/blog/1579192里面说的比较详细了,基本就是照里面实现的。

能够随心所欲的控制map和reduce的数量之后,hive代码的质量确实好了很多,每个脚本的时间从70分钟缩短到了20分钟,每条sql再也不是可怜兮兮的2个map。而是20个map了。

你可能感兴趣的:(hive优化)