我在Hive中使用左连接插入记录。当我设置限制1查询工作,但对于所有记录查询卡在99%减少作业。
下面的查询有效
Insert overwrite table tablename select a.id , b.name from a left join b on a.id = b.id limit 1;
但这不是
Insert overwrite table tablename select table1.id , table2.name from table1 left join table2 on table1.id = table2.id;
我已经增加了减速器的数量,但它仍然不工作
这里有一些Hive优化,可以帮助查询优化器并减少在线发送数据的开销。
set hive.exec.parallel=true;
set mapred.compress.map.output=true;
set mapred.output.compress=true;
set hive.exec.compress.output=true;
set hive.exec.parallel=true;
set hive.cbo.enable=true;
set hive.compute.query.using.stats=true;
set hive.stats.fetch.column.stats=true;
set hive.stats.fetch.partition.stats=true;
然而,我认为潜在的问题更有可能是连接中的关键。有关倾斜的完整描述和可能的解决方法,请参阅https://cwiki.apache.org/confluence/display/Hive/Skewed+Join+Optimization
您还提到table1比table2小得多。您可以根据硬件约束尝试映射端连接。(https://cwiki.apache.org/confluence/display/Hive/LanguageManual +连接)
如果您的查询卡在99%,请检查以下选项-
- 数据偏度,如果你有偏度的数据,可能有一个减速器正在做所有的工作
- 在两边重复键-如果你在两边有很多重复的连接键,你的输出可能会爆炸,查询可能会卡住
- 如果你的表很小,尝试使用map连接,或者如果可能的话,使用SMB连接,这比减少侧连接有很大的性能提升 进入资源管理器日志,查看正在访问和写入的数据作业的数量。
当涉及到连接时,Hive会自动进行一些优化,并在符合要求的情况下将连接的一侧加载到内存中。然而,在某些情况下,这些工作停留在99%,从未真正完成。
我已经遇到过很多次了,我通过显式地为hive指定一些设置来避免这种情况。试试下面的设置,看看是否适合你。- hive.auto.convert。加入= false
- mapred.compress.map.output = true
- hive.exec.parallel = true
确保您的数据表中没有具有重复id值的行!
我最近遇到了同样的问题,左连接的map-reduce进程在Hue中卡住了99%。
经过一番窥探,我发现了问题的根源:在我的一个表中有重复member_id匹配变量的行。左连接所有重复的member_ids将创建一个包含数亿行的新表,消耗的内存超过了我在公司Hadoop服务器上分配的内存。
使用这些配置并尝试hive> set mapreduce.map.memory.mb=9000;
hive> set mapreduce.map.java.opts=-Xmx7200m;
hive> set mapreduce.reduce.memory.mb=9000;
hive> set mapreduce.reduce.java.opts=-Xmx7200m
我在左外连接中遇到了类似的问题:
select bt.*, sm.newparam from
big_table bt
left outer join
small_table st
on bt.ident = sm.ident
and bt.cate - sm.cate
我根据已经给出的答案做了一个分析,我看到了两个给定的问题:
左表比右表大100倍以上
select count(*) from big_table -- returned 130M
select count(*) from small_table -- returned 1.3M
我还检测到其中一个连接变量在右表中相当倾斜:
select count(*), cate
from small_table
group by cate
-- returned
-- A 70K
-- B 1.1M
-- C 120K
我尝试了其他答案中给出的大多数解决方案以及我在这里找到的一些额外参数,但没有成功:
set hive.optimize.skewjoin=true;
set hive.skewjoin.key=500000;
set hive.skewjoin.mapjoin.map.tasks=10000;
set hive.skewjoin.mapjoin.min.split=33554432;
最后,我发现左表的连接列的空值百分比非常高:: bt.ident
和bt.cate
所以我尝试了最后一件事,最终为我工作:根据bt.ident
和bt.cate
是否为空来分割左表,稍后与两个分支一起制作union all
:
select * from
(select bt.*, sm.newparam from
select * from big_table bt where ident is not null or cate is not null
left outer join
small_table st
on bt.ident = sm.ident
and bt.cate - sm.cate
union all
select *, null as newparam from big_table nbt where ident is null and cate is null) combined