Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/oracle/9.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/xml/15.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Oracle WHERE子句限制行左连接_Oracle_Join - Fatal编程技术网

Oracle WHERE子句限制行左连接

Oracle WHERE子句限制行左连接,oracle,join,Oracle,Join,我不明白为什么下面这两个查询的计数不同。下面的案例1获取的行数更多,而案例2获取的行数更少。如果将where子句放在外部,则获取的记录会更少 案例1 SELECT COUNT(1) FROM ( SELECT * FROM (SELECT * FROM TABLE1 WHERE COL1 = 123) A LEFT JOIN TABLE2 B ON B.COL2=A.COL4 LEFT JOIN TABLE3 C ON C.COL3=B

我不明白为什么下面这两个查询的计数不同。下面的案例1获取的行数更多,而案例2获取的行数更少。如果将
where
子句放在外部,则获取的记录会更少

案例1

SELECT COUNT(1) 
FROM (
    SELECT * 
    FROM (SELECT * FROM TABLE1 WHERE COL1 = 123) A
          LEFT JOIN TABLE2 B ON B.COL2=A.COL4
          LEFT JOIN TABLE3 C ON C.COL3=B.COL2
      )
案例2

SELECT COUNT(1) 
FROM (
    SELECT * 
    FROM (SELECT *  FROM TABLE1 ) A
         LEFT JOIN TABLE2 B ON B.COL2=A.COL4
         LEFT JOIN TABLE3 C ON C.COL3=B.COL2
   ) 
WHERE COL1 = 123

理论解释:

考虑表a和表B的左外部联接。表B上的条件(筛选器)在联接条件(on子句)和WHERE子句中具有不同的效果编辑:B上的过滤器处于on状态相当于用首先应用过滤器的子查询替换B(类似于OP的示例)

如果它在ON子句中,那么表B中的行将针对该条件进行筛选,然后执行左连接。然后,只要B中没有满足筛选条件且与连接条件上的A中的行匹配的行,查询结果就会包括A中的行(B侧为NULL)

另一方面,如果B上的过滤器在执行的后面,在WHERE子句中,则首先执行左连接。只有这样,WHERE子句才适用。WHERE子句很可能(取决于B上的条件)拒绝A中没有匹配行的所有行,因为对于这些行,B中的所有值都为NULL


在您的例子中,假设COL1只存在于表B中,那么WHERE子句中的条件COL1=123将有效地导致左连接产生与内部连接相同的结果:a中与B中不匹配的任何行将来自左连接,COL1为NULL,因此它们将使筛选条件失败。在ON子句中输入COL1=123时,该检查在“外部联接”操作之前完成。

请发布一些复制此行为的示例数据。理论上这是可能的,但如果没有示例数据,则很难解释结果谢谢回复。然而,如果你能提供理论上的解释也会有所帮助(可能会有帮助的事情:1)选择一个更具说服力的标题2)问一个明确的问题3)让DB解释一个执行计划)当你在这里发布时,你确定你正确地转换了你的实际例子吗?我不这么认为。如果从子查询移动到外部查询的筛选器位于左外部联接的左表上,则该移动将无效。如果你不这么说,请提供一个具体的例子。(不要浪费你的时间;回到你的真实例子,找出你翻译错误的地方。)半简洁的解释。如果您使用的表
A
B
与OP匹配,而不是翻转它们,那么会更整洁。@APC-我故意没有阅读OP的示例,因为他要求理论解释。我甚至不打算添加最后一段,但在我完成后,我觉得它可能太理论化了。@APC-err。。。现在我读了OP的例子,OP是错误的。这些查询应该产生相同的结果,因为过滤器位于左联接左侧的表上。这样的过滤器可以在ON或WHERE子句中,没有区别。我会要求澄清。是的,你是对的,我得到的行数较少是因为查询中的一些其他条件(排名),而不是因为左连接。我还想知道这是怎么可能的,在示例中where子句的左连接位置应该不重要。谢谢