混淆'和'过滤内部
问题描述:
可以解释HiveQL中这两个查询之间的区别。基本上我想从table a
过滤掉日期大于2017-05-01。第二个查询没有给出我预期的结果,但是第一个查询得到了结果。我以为他们是相当于混淆'和'过滤内部
select a.user_id
, b.user_id
, a.event_date
, b.event_date
, to_date(a.event_date)
from default.t1 as a
left join stage.t2 as b
on a.user_id = b.user_id
and a.event_date = b.event_date
where a.event_date >= '2017-05-01'
与
select a.user_id
, b.user_id
, a.event_date
, b.event_date
, to_date(a.event_date)
from default.t1 as a
left join stage.t2 as b
on a.user_id = b.user_id
and a.event_date = b.event_date
and a.event_date >= '2017-05-01'`
答
A left join
保留第一个表中的所有行,而不管on
子句是否计算结果为true。当on
子句的计算结果为true时,它也具有第二个表中的所有匹配行。否则,第二个表中的列是NULL
。
因此,left join
基本上忽略了第一个表上的任何过滤条件。无论如何,它都会保留第一个表中的行。
事实上,情况稍微复杂一些。如果on
条件未评估为真,则第二个表中的列全部为NULL
。因此,在第二个查询中,当日期不匹配时,b
中的列应为NULL
。
怎么办?
-
left join
中的第一个表上的条件应始终在where
子句中。 - 第二张桌子上的条件应该始终在
on
条款中。
+0
感谢提示何时在'on'和'where'子句中使用过滤器。我一直有困难缠绕我的头(不能想象它在我的头上) – lollerskates
答
我发现类似的问题,由金达尔@Sandeep的回答是最好的
SQL join: where clause vs. on clause
一个。 WHERE子句:加入后。记录将在联接发生后被过滤。
b。 ON条款 - 加入前。记录(来自右表)将在加入前被过滤。这可能会以结果为空(因为外部连接)。
您正在使用'left join',所以在第一个查询中,您将得到结果,其中'b.event_date'可以为null,然后筛选最终结果....在第二个日期条件中在连接中,所以你确保首先得到正确的数据....这是我的理解,但是,有人可以得到更好的解释 – Hackerman