连接语句操作顺序

Posted

技术标签:

【中文标题】连接语句操作顺序【英文标题】:Join statement order of operation 【发布时间】:2012-09-21 06:45:47 【问题描述】:

给定以下3种方式加入

select t1.* from t1
left join t2 on t1.fk = t2.pk
join t3 on t2.fk = t3.pk

如果 t2 和 t3 之间的连接失败,是否会返回 t1 和 t2 之间连接成功的行?如果操作顺序是从左到右,我假设不是,但是如果它是从右到左计算的(t3 先连接到 t2),那么即使前者失败,t1 仍然会返回。

它是如何工作的?

【问题讨论】:

【参考方案1】:

ON 子句的位置控制评估的逻辑顺序。

所以首先发生t1 LEFT JOIN t2 ON t1.fk = t2.pk。此连接的结果是一个虚拟表,其中包含来自t1, t2 的所有匹配行,并且(因为它是左外连接)任何不匹配的t1 行也将保留为t2 列的空值。

然后这个虚拟表参与下一个连接。 JOIN t3 ON t2.fk = t3.pk

任何与t1 中的行不匹配的t2 记录都不是第一阶段的虚拟表输出的一部分,因此不会出现在最终结果中。此外,t2.fk = t3.pk 上的此内部联接将丢失 t2.fk 的任何 NULL 值,从而有效地将您的整个事物重新转换为内部联接。

逻辑查询处理很好解释by Itzik Ben Gan here

【讨论】:

回答的重点,讲解的很全面。感谢您的帮助。 很好很简单的解释我想知道相同的操作顺序是否适用于sqlite @MuhammadBabar - 我没有使用过 SQLLite,但如果它符合标准 (ANSI/ISO) SQL,它会。 希望它坚持。好的,如果我将上述查询修改为select t1.* from t1 inner join t2 on t1.fk = t2.pk left join t3 on **t1.fk** = t3.pk 会发生什么 @MuhammadBabar - 第一部分是。第二个连接将应用于从第一个连接获得的虚拟表。拒绝第二部分,因为没有任何东西可以保证 t2.fk 和 t1.fk 的值相同,因此查询可能返回不同的结果,但这不会改变逻辑描述。

以上是关于连接语句操作顺序的主要内容,如果未能解决你的问题,请参考以下文章

sql语句--添加数据--修改语句--删除语句---连接查询

MySQL学习笔记连接子分页联合查询以及sql语句执行顺序总结

mysql执行顺序及左连接和右连接

SQL语句中连接on条件和where条件的执行顺序

SQL语句操作优先级顺序

mysql 语句执行顺序