我有三个表: R,S和P。
表R通过外键与S连接;S中应该至少有一条记录,所以我可以连接:
SELECT
*
FROM
R
JOIN S ON (S.id = R.fks)
如果在S中没有记录,那么我就不会得到行,这是很好的。
则表S与P连接,其中记录为P,可能存在也可能不存在,并与S连接。
我就是这么做的
SELECT
*
FROM
R
JOIN S ON (S.id = R.fks)
LEFT JOIN P ON (P.id = S.fkp)
如果我希望第二个连接绑定到S而不是R,比如我可以使用括号:
SELECT
*
FROM
R
JOIN (S ON (S.id = R.fks) JOIN P ON (P.id = S.fkp))
或者,这是笛卡尔乘积在R,S和P之间的一种自然行为吗?
发布于 2011-06-18 04:07:55
所有类型的外部连接和普通连接都在同一个优先级类中,并且运算符在查询的给定嵌套级别上从左到右生效。您可以将连接表达式放在右侧的圆括号中,以使其首先生效。请记住,您必须移动ON
子句,以便它们与它们的连接保持一致-括号中的连接将其ON
子句一起放入括号中,因此它现在文本上位于其他ON
子句之前,后者将位于外部join语句中的括号之后。
(PostgreSQL示例)
在SELECT * FROM a LEFT JOIN b ON (a.id = b.id) JOIN c ON (b.ref = c.id);
中
a-b连接首先生效,但我们可以通过将b-c连接放在括号中来强制b-c连接首先生效,如下所示:
SELECT * FROM a LEFT JOIN (b JOIN c ON (b.ref = c.id)) ON (a.id = b.id);
通常,你可以通过移动连接和改变外部连接的方向来表达相同的东西,而不需要额外的括号,例如
SELECT * FROM b JOIN c ON (b.ref = c.id) RIGHT JOIN a ON (a.id = b.id);
发布于 2010-09-24 00:11:59
连接第三个表时,您的第一个查询
SELECT
*
FROM
R
JOIN S ON (S.id = R.fks)
类似于您要连接到的第三个表的派生表。因此,如果R JOIN S
没有生成任何行,那么连接P
将永远不会生成任何行(因为您正在尝试连接到一个空表)。
因此,如果您正在寻找优先级规则,那么在本例中,它是使用LEFT JOIN
而不是JOIN
来设置的。
但是,我可能误解了您的问题,因为如果我编写查询,我会交换S
和R
。例如:
SELECT
*
FROM
S
JOIN R ON (S.id = R.fks)
发布于 2010-09-24 00:03:06
第二个连接被绑定到S,因为您显式地声明了JOIN P ON (P.id = S.fkp)
-在连接中没有引用来自R的列。
https://stackoverflow.com/questions/3780199
复制相似问题