我有三张桌子AA,BB和CC。 BB和CC具有一对一映射到表AA(具有外键列:两个表中的aa_id)。提供了一个条件,即只有BB或CC可以引用一行表AA。
我想从AA中选择最新 1000行,或者加入BB或CC。 我可以单独查询以选择500行分别与BB和CC连接并生成1000.但这并不能保证我从AA表中获取最新的1000行。
所以,我想出了以下查询,通过同时加入BB和CC从AA中选择记录。但是由于我的限制(只有BB或CC可以引用一行表AA),我从下面的查询得到0行。
SELECT * FROM AA
INNER JOIN BB ON (
AA.id = BB.aa_id
AND SOME_CONDITION
)
INNER JOIN CC ON (
AA.id = CC.aa_id
AND SOME_CONDITION
)
ORDER BY
AA.id DESC limit 1000;
你能告诉我怎么做吗?有没有什么方法可以让我这两个JOIN条件?
答案 0 :(得分:3)
只需将INNER JOIN
更改为LEFT OUTER JOIN
,您就可以了。您可能需要阅读this article on codinghorror.com以获取不同连接类型的说明。
您的结果应如下所示:
SELECT * FROM AA
LEFT OUTER JOIN BB ON (
AA.id = BB.aa_id
AND /* SOME_CONDITION */
)
LEFT OUTER JOIN CC ON (
AA.id = CC.aa_id
AND /* SOME_CONDITION */
)
ORDER BY AA.id DESC
LIMIT 1000;
答案 1 :(得分:1)
由于BB
中的每一行CC
或AA
只有一个匹配,因此您应将INNER JOIN
替换为LEFT OUTER JOIN
。< / p>
所以查询应该是:
SELECT * FROM AA
LEFT OUTER JOIN BB ON (
AA.id = BB.aa_id
AND SOME_CONDITION
)
LEFT OUTER JOIN CC ON (
AA.id = CC.aa_id
AND SOME_CONDITION
)
ORDER BY
AA.id DESC limit 1000;
答案 2 :(得分:1)
如果您想要AA中的所有记录,其中BB或CC中的相应记录存在,您甚至不必加入(假设您不需要BB和CC中的值) 。请改用EXISTS
:
SELECT * FROM AA
WHERE
(
EXISTS (
SELECT 1 FROM BB WHERE AA.id = BB.aa_id
/* AND SOME_CONDITION */
) OR EXISTS (
SELECT 1 FROM CC WHERE AA.id = CC.aa_id
/* AND SOME_CONDITION */)
)
ORDER BY AA.id DESC limit 1000;
对我来说看起来更干净(而且它可能会更快一些,因为处理的数据更少,但我还没有对其进行测试)!
答案 3 :(得分:0)
编辑:你说'最后1000行的AA',所以要注意在选择中指定AA。*,否则你将获得由AA组成的1000行,然后是所有字段BB和CC的所有字段(两个集合中的一个也将为NULL)。
这将获得与BB或CC(或两者)匹配的最后1000行AA:
SELECT AA.* FROM AA
LEFT JOIN BB ON (
AA.id = BB.aa_id
AND SOME_CONDITION
)
LEFT JOIN CC ON (
AA.id = CC.aa_id
AND SOME_CONDITION
)
WHERE (BB.aa_id IS NOT NULL OR CC.aa_id IS NOT NULL)
ORDER BY AA.id DESC LIMIT 1000;
答案 4 :(得分:0)
@oezi是绝对正确的。您的查询中只需要进行少量更改,只需删除INNER JOIN
即可。使用LEFT OUTER JOIN
AND
条件作为@oeze提及。