Hive中Join的通常使用有以下几种:
join_a.txt:
1 zhangsan
2 lisi
3 wangwu
join_b.txt:
1 30
2 29
4 21
创建a表并导入数据:
create table a(
id int,name string
)
row format delimited fields terminated by '\t';
hive>load data local inpath '/opt/data/join_a.txt' overwrite into table a;
创建b表并导入数据:
create table b(
id int,age int
)
row format delimited fields terminated by '\t';
hive>load data local inpath '/opt/data/join_b.txt' overwrite into table b;
hive>select a.id,a.name,b.age from a join b on a.id=b.id;
hive>select a.id,a.name,b.age from a left join b on a.id=b.id;
hive>select a.id,a.name,b.age from a right join b on a.id=b.id;
hive>select a.id,a.name,b.age from a full join b on a.id=b.id;
hive>select a.id,a.name,b.age from a cross join b;
地址:http://blog.csdn.net/lemonzhaotao/article/details/78209708
由于Hive的底层就是MapReduce,因此通过MapReduce的自己编程,可以进一步了解两者的执行原理,有助于Hive的学习
Common Join即传统思路实现Join,性能较差 因为涉及到了shuffle的过程
common join/shuffle join/reduce join (都是指同一个)
有a表和b表
以这句SQL为思路: select a.id,a.name,b.age from a join b on a.id=b.id 去实现
通过两个表的id去进行join
1) map 读取 a表 ==> <id, (name)>
<1,(zhangsan)>
<2,(lisi)>
<3,(wangwu)>
2) map 读取 b表 ==> <id, (age)>
<1,(30)>
<2,(29)>
<4,(21)>
3) shuffle: hash(key)
<1,(zhangsan,30)>
<2,(lisi,29)>
<3,(wangwu)>
<4,(21)>
4) reduce
1,(zhangsan,30)
2,(lisi,29)
3,(wangwu)
4,(21)
mapjoin 也叫作 boardcast join
map join不会有reduce阶段和shuffle阶段
通过日志打印的信息去对比两种Join操作
非常重要,需要会画两个join的图、知道两者的原理
dept.txt
10 ACCOUNTINGNEW YORK
20 RESEARCHDALLAS
30 SALESCHICAGO
40 OPERATIONSBOSTON
hive>create table dept(deptno int, dname string, loc string) row format delimited fields terminated by '\t';
hive>load data local inpath '/opt/data/dept.txt' overwrite into table dept;
hive低版本使用mapjoin必须这样写:
得说明d是小表:/+MAPJOIN(d)/ 告诉hive d是小表
hive>select /*+MAPJOIN(d)*/ e.empno, e.ename, d.dname from emp e join dept d on e.deptno=d.deptno;
注意:在hive中看执行计划是十分重要的一个技能
网址:
https://cwiki.apache.org/confluence/display/Hive/LanguageManual+Explain
语法:
EXPLAIN [EXTENDED|DEPENDENCY|AUTHORIZATION] query
hive.auto.convert.join参数设置
hive.auto.convert.join=true的意思为:
hive自动会把普通的join转换为mapjoin,也就是哪个表大哪个表小 hive自动会我们进行转换
为了测试看到更好的效果,我们需要将这个值设置为false
给参数设置值
hive>set hive.auto.convert.join=false;
hive>explain select e.empno, e.ename, d.dname from emp e join dept d on e.deptno=d.deptno;
打印出信息的部分说明:
TableScan 表示去读表
Filter Operator 表示过滤操作 即 e.deptno=d.deptno
value expressions 表示输出的value字段有哪些
hive>set hive.auto.convert.join=true;
hive>explain select e.empno, e.ename, d.dname from emp e join dept d on e.deptno=d.deptno;
starting to launch local task
对应 mapreduce local task
Dump ….. hashtable
将hashtable sink出来了(输出出来)
uploaded ….
将hashtable 上传到分布式缓存中了 这个就是小表的流程
End of local task
结束了local task
MapredLocal task successfully
map local task执行成功
Launching Job 1 out of 1
启动一个job
number of mappers:1 number of reducers:0
没有reducer,mapper数量为1
重点:
对于普通join 会生成2个stage
对于mapjoin 会生成3个stage