如果表已加入,Where Statement是否重要?

时间:2017-01-11 12:59:17

标签: sql oracle

我想知道两个查询是否总会返回相同的结果。他们是平等的吗?

SELECT OT_ACC_NO , ACC_NO FROM ACCOUNTS
JOIN OTHER_TABLE ON OT_ACC_NO = ACC_NO
WHERE ACC_NO IS NOT NULL 

SELECT OT_ACC_NO , ACC_NO FROM ACCOUNTS
JOIN OTHER_TABLE ON OT_ACC_NO = ACC_NO
WHERE OT_ACC_NO IS NOT NULL

4 个答案:

答案 0 :(得分:5)

这两个是等价的。或许更令人惊讶的是WHERE子句是不必要的。所以,这是等价的:

SELECT OT_ACC_NO, ACC_NO
FROM ACCOUNTS JOIN
     OTHER_TABLE
     ON OT_ACC_NO = ACC_NO;

为什么呢?因为INNER JOIN仅在ON条件为 true 时才返回行。如果任一值为NULL,则比较返回NULL,其被视为 false

我应该注意,虽然最终结果是相同的,但查询的执行计划可能不一样。

答案 1 :(得分:3)

此条件不会产生任何逻辑影响。

INNER JOIN确保记录必须存在于两个表中,并且它们不能是NULL值。

答案 2 :(得分:2)

让我们向后退一步,考虑相等运算符和NULL值:

SELECT CASE WHEN NULL = NULL THEN 'Equal' ELSE 'Not Equal' END FROM DUAL;

现在,令人惊讶的是,有些人会返回Not Equal

如果您认为NULL表示未知值,那么您会询问未知值是否等于另一个未知值且答案是否为假。

查询:

SELECT OT_ACC_NO,
       ACC_NO
FROM   ACCOUNTS
       JOIN OTHER_TABLE
       ON OT_ACC_NO = ACC_NO

这将在OT_ACC_NO = ACC_NO时加入表格,如上所述,如果这些变量中的任何一个是NULL(未知),则相等比较的结果将始终为false,行将为被排除在加入结果之外。

因此,添加一个where子句来测试OT_ACC_NOACC_NO是否为NULL将永远不会排除任何行,因为它们已被连接条件排除。

答案 3 :(得分:0)

问题标有Oracle,因此答案应该以某种方式仔细查看无逻辑影响等效相同结果的主题

下面的示例数据,其中秒查询没有返回任何数据,但第一个查询失败并显示ORA-01722: invalid number

create table ACCOUNTS as
select '1-1'  ACC_NO from dual;


create table OTHER_TABLE as
select cast(null as number) OT_ACC_NO from dual;