Hive优化—skew join优化原理详解

优化原理

JOIN中倾斜键的处理思路最早是在HIVE-964中提出的,整体思路是使用独立的作业和mapjoin来处理倾斜的键。

用以处理倾斜键的MR作业数是表的数量减一(we can stream the last table, so big keys in the last table will not be a problem)

在执行JOIN的过程中,会将一个表中的大key(也就是倾斜的那部分数据,判断是否倾斜由配置项hive.skewjoin.key指定,默认是100000)输出到一个对应的目录中,同时该key在其他表中的数据输出到其他的目录中(每个表一个目录)。整个目录结构类似下面这样:

  • T1表中的大key存储在目录 dir-T1-bigkeys中,这些key在T2表的数据存储在dir-T2-keys中,这些key在T3表的数据存储在dir-T3-keys中,以此类推。。。
  • T2表中的大key在T1中的数据存储在 dir-T1-keys,T2表中的大key存储在目录dir-T2-bigkeys中,这些key在T3表的数据存储在dir-T3-keys中,以此类推。。。
  • T3表中的大key在T1中的数据存储在 dir-T1-keys,这些key在T2表的数据存储在dir-T2-keys中,T3表中的大key存储在目录dir-T3-bigkeys中,以此类推。。。

对于每个表,都会单独启动一个mapjoin作业处理,输入的数据,就是该表的大key的目录和其他表中这些key对应的目录,对于上面情况基本就是会启动三个map join作业(一行对应一个)

对于每个表中每一个倾斜键(skew key一个表中可能会有多个倾斜键)首先会写入到本地的一个临时文件中,最后将这些文件上传到HDFS中。

下面是一张在网上找到的图片,可以帮助我们理解优化过程
在这里插入图片描述

适用范围

Hive包含有INNER JOIN,UNION JOIN,LEFT OUTER JOIN, RIGHT OUTER JOIN, FULL OUTER JOIN等多种JOIN类型,那么这些JOIN都能够适用skew join优化吗?

在Hive中,用于处理skew join的类主要有GenMRSkewJoinProcessor和GenSparkSkewJoinProcessor,他们都在org.apache.hadoop.hive.ql.optimizer.physical package中,从名字上就可以看出他们分别用以MR和Spark引擎,事实上GenSparkSkewJoinProcessor是直接拷贝的GenMRSkewJoinProcessor,因此二者逻辑上完全一样。

在这两个类中,是否能够使用skew join优化,是有条件中,如果不满足条件,是无法使用skew join 优化特性的。如下代码截图,可以看到这里调用GenMRSkewJoinProcessor.skewJoinEnabled()来判断是否能够使用优化。
在这里插入图片描述
看一下GenMRSkewJoinProcessor.skewJoinEnabled方法的实现:
在这里插入图片描述
从上面的代码中,可以看到要使用skew join优化,必须满足如下的条件:

  1. 开启优化特性,也就是hive.optimize.skewjoin配置项必须是true,默认是false,这一点想必都很熟悉了。
  2. 不能是outer join,这里只是简单的说outer join 不能使用倾斜优化,那么这些outer join 具体包括哪些呢?

继续查看源码后最终发现这个值的设置是通过QBJoinTree.setNoOuterJoin()方法完成的,进一步发现在SemanticAnalyzer类中多次调用了这个方法,并且将这个值设置为false。
在这里插入图片描述
在这里插入图片描述
到这里就可以知道在Hive中,UNION JOIN,LEFT OUTER JOIN, RIGHT OUTER JOIN, FULL OUTER JOIN 这几种join是无法使用skew join优化的。只有INNER JOIN才可以!

测试验证

在开启倾斜优化后,会在task(hive on spark)中看到如下的日志信息:
在这里插入图片描述
上面的日志说明,hive对这些超过了hive.skewjoin.key配置项指定阈值的key从本地拷贝到了一个HDFS目录中,这一点和文章开头的分析一致

然后看一下,对应的HDFS目录中的结构,可以看到两张表的数据,大表的数据会划分到了多个目录中,另一张较小的表的目录结构与大表的目录结构一致
在这里插入图片描述
小表中每个子目录中数据是完全一样的
在这里插入图片描述
另外从task的执行日志可以看到其使用了skewjoin优化
在这里插入图片描述
参考
https://www.chinahadoop.cn/course/597/learn#lesson/12014

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值