hive where字句里不允许有子查询
不支持如下:
select ...
from table_name
where id in (select id from ... )
这种语法hive里面是不支持的,但是关系型数据库里面经常会这么写。
如何替换:我们可以用两个表关联代替,但是in右边括号里边是不允许重复的,而关联时右边是有重复的。所以就是说,我们应该先把join右边的表进行去重,然后再进行关联,就可以替换in了
not in
select ...
from table_name
where not id in (select id from...)
not in 用left outer join ... where col is null
关系型数据库的语法:
select a.key, a.value
from a
where a.key not in
(select b.key
from b);
替换方式
select a.key
from a
left outer join b on a.key = b.key
where b.key is null;
======================================一个小插曲揭示下左外和右外==============================
通俗的讲:
A left join B 的连接的记录数与A表的记录数同
A right join B 的连接的记录数与B表的记录数同
A left join B 等价B right join A
table A:
Field_K, Field_A
1 a
3 b
4 c
table B:
Field_K, Field_B
1 x
2 y
4 z
select a.Field_K, a.Field_A, b.Field_K, b.Field_B
from a left join b on a.Field_K=b.Field_K
Field_K Field_A Field_K Field_B
---------- ---------- ---------- ----------
1 a 1 x
3 b NULL NULL
4 c 4 z
select a.Field_K, a.Field_A, b.Field_K, b.Field_B
from a right join b on a.Field_K=b.Field_K
Field_K Field_A Field_K Field_B
---------- ---------- ---------- ----------
1 a 1 x
NULL NULL 2 y
4 c 4 z --
===========================
LEFT SEMI JOIN
hive当前没有实现exists,所以你可以用left semi join
重写你的子查询语句。left semi join的限制是,join字句中右边的表只能在on字句中设置过滤条件,在where字句,select字句或其他地方过滤都不行
select a.key, a.value
from a
where a.key in
(select b.key
from b);
可以重写为:
select a.key,a.val
from a left semi join b on (a.key = b.key)
或者select a.key, a.val
from a join (select distinct b.key from b) b on a.key = b.key
hive是mapreduce写的,所以hive优化很大关系也是mapreduce优化
中间参数一般情况下企业开发都不调。因为调中间参数,很容易失控,带来灾难性后果
hadoop内幕:
map阶段产生的中间结果不保存到磁盘,而是保存到中间buffer中,当buffer数据达到一定量,再批量往磁盘写,不是buffer满了才往磁盘写,默认是有个百分之八十的比例
对中间的数据的压缩是非常值得的,因为通常来说,压缩能够把数据量压缩百分之九十,虽然增减了cpu负载,但是这种压缩是值得的。
做优化的时候通常要先找到瓶颈在哪里,再进行优化。
目前行业内hive的竞争对手:
impala :cloudera公司的一个产品,用的也是sql,和hive共享元数据库,也用hive的元数据库,性能比hive高好几倍。它不是基于mapreduce,有自己的计算框架,目前还不太成熟,企业用的不多,市场不太好,和cloudera有关系,这个公司是做产品的,而不是做数据的。而hive是facebook推出的。
presto:facebook推出的,也是一个sql的产品,处理能力比hive高很多,目前开源的内容上功能不太强大,不能替代hive,还没有吧所有功能开源
Pig:类sql
做离线处理,用hive足够了,如果对实时性要求很高,也可以用其他技术,presto再强也是离线统计的,因为他是在磁盘里面的
上面的所有产品都是非实时的,因为他们把数据放在磁盘上面了,然后读,查询计划再好也是非实时。
实时处理:storm 数据未持久化之前就进行处理,处理完之后可以再去持久化。