我们可以通过这两种方式获得相同的结果。
Table_1 LEFT OUTER JOIN Table_2
Table_2 RIGHT OUTER JOIN Table_1
如果我们可以得到相同的结果,为什么要使用右外连接?哪一个更好?
答案 0 :(得分:13)
正如其他人已经指出的那样LEFT OUTER JOIN
和RIGHT OUTER JOIN
是完全相同的操作,除非它们的参数被颠倒过来。您的问题就是询问编写a < b
或b > a
是否更好。它们是相同的 - 这只是一个偏好问题。
话虽如此,我发现大多数人都更熟悉LEFT JOIN
并在SQL中一致地使用它。如果查询中间突然出现RIGHT JOIN
,有些人甚至发现很难阅读,这导致他们不得不停下来思考它意味着什么。所以我建议在两个选项之间给出相同的选择,更喜欢使用LEFT JOIN
。保持一致将使其他开发人员更容易理解您的SQL。
答案 1 :(得分:4)
这些是平等的,只是偏好和可读性的问题。我假设它是相同的表?
答案 2 :(得分:2)
左外连接
表A和B的左外连接(或简称左连接)的结果始终包含“左”表(A)的所有记录,即使连接条件未在“”中找到任何匹配记录右“表(B)。这意味着如果ON子句匹配B中的0(零)记录,则连接仍将在结果中返回一行 - 但在B的每一列中都为NULL。这意味着左外连接返回所有值从左表开始,加上右表中的匹配值(如果没有匹配的连接谓词,则为NULL)
正确的外部加入
右外连接(或右连接)非常类似于左外连接,除了表格的处理方式。 “右”表(B)中的每一行将至少出现在连接表中一次。如果“左”表(A)中没有匹配的行,则A中的列中将出现NULL对于那些在B中没有匹配的记录。右外连接返回右表中的所有值和左表中的匹配值(如果没有匹配的连接谓词,则为NULL)。
答案 3 :(得分:2)
SQL语言的设计者正确地认为强制从左到右的连接优先级将是对语言的不必要的约束(遗憾的是,他们对列排序感觉不一样!)
似乎在Stackoverflow上强烈偏好LEFT OUTER
,以至于民众会改变整个联接只是为了能够使用LEFT
(我们有一个here就在昨天)。
假设您最初在查询Table_2 INNER JOIN Table_1
中写过,之后才意识到您确实需要一个外部联接来保留Table_1
中的所有行。将INNER
更改为RIGHT OUTER
比将整个联接更改为能够使用LEFT OUTER
要简单得多。这里很简单,因为它的侵入性较小,因此无意中更改了查询意图的风险。
要使用其他类似示例,请考虑关系运算符semi join;作为关系代数的一部分,没有它,技术就不能被认为是关系完整的。尽管标准SQL确实具有半连接谓词MATCH
,但它并未广泛实现。但是,大多数SQL产品都支持各种解决方法。在Stackoverflow上看到的最常见的方法似乎是在INNER JOIN
子句中使用DISTINCT
和SELECT
,并省略连接表中的属性。紧随其后的是使用WHERE table_1.ID IN (SELECT ID FROM Table_2)
。其次最受欢迎的是WHERE EXISTS (SELECT * FROM Table_2 WHERE table_1.ID = table_1.ID)
。
关键是,以上都是在野外非常常见的半连接。虽然我个人倾向于使用EXISTS
(虽然奇怪的是它更接近关系演算),但我仍然需要能够将其他人识别为半连接;有趣的是,最流行的方法(INNER JOIN
加DISTINCT
加非投影)可能是最难识别的方法!
仅仅为了适合个人风格而重构代码是正确的:不必要的努力成本,增加风险,源头控制的含义等。学会认识和尊重他人的偏好是一项重要的技能:如果你发现自己重构只是为了能够理解它,你将使自己处于劣势。
当然,从关系上讲,“正确”的答案是完全避免外部联接。在关系模型中没有null这样的东西,外连接被明确地设计为产生空值。
答案 4 :(得分:1)
这取决于我们的需要 - 我们是否需要来自Left table或Right table的所有列。
两者都不一样。