【问题标题】:SQL: Query where column = x, when column2 != y; y = column when column2 = x..if that makes senseSQL: 查询 where column = x, when column2 != y; y = column 当column2 = x ..如果这是有道理的
【发布时间】:2013-03-06 06:15:40
【问题描述】:

所以我有这张桌子:

PK | FK1 | FK2
1  | 1   | 2
2  | 1   | 3
3  | 1   | 6
4  | 2   | 1
5  | 2   | 6
6  | 5   | 3

PK 是主键 (dur)。 FK1 和 FK2 是其他表中同一列的外键(不相关)。

查询类型 1

我想获取 FK1 = x 的所有行。但与此同时,我不想包含 FK2 = y; 的行。 y 是 FK1,其中 FK2 = x。另一种说法是:FK1 = x,但 FK2 不能等于 FK2 = x 表中 FK1 的任何值。例如,x = 1:

PK | FK1 | FK2 | Returned in Result Set (Yes = √, No = x)
1  | 1   | 2   | x
2  | 1   | 3   | √
3  | 1   | 6   | √
4  | 2   | 1   | x
5  | 2   | 6   | x
6  | 5   | 3   | x

注意,PK >= 4 的行不包括在结果集中,因为 FK1 != 1。但是,PK = 1 的行不包括在结果集中,而 FK1 = 1。为什么?因为 FK2 = 2,当 FK2 = x 或 1 在 PK = 4 的那一行时,这就是 FK1 的值。如果遇到问题,请多读几遍。

查询类型 2

这几乎就像第一种查询。我想获取 FK2 = x 和 FK1 != y 的所有行,其中 y = FK2,其中 FK1 = x。相同,只是列颠倒了。我的重点是 FK2,而不是 FK1。

查询类型 3

我想获取 FK1 = x 的所有行,仅当 FK2 = y 时; y = FK1,其中 FK2 = x。希望你一直在遵循 x 和 y 的约定,所以我不需要解释太多。这是一个例子,x = 1:

PK | FK1 | FK2 | Returned in Result Set (Yes = √, No = x)
1  | 1   | 2   | √
2  | 1   | 3   | x
3  | 1   | 6   | x
4  | 2   | 1   | x
5  | 2   | 6   | x
6  | 5   | 3   | x

只返回第一行,PK = 1。为什么?因为 FK1 = x 或 1,而 FK2 = y 或 2,即 FK1,其中 FK2 = 1(第 4 行)。

伙计,我希望这是有道理的。告诉我我从哪里开始说不通,我会编辑。

感谢阅读。感谢所有帮助。

【问题讨论】:

    标签: mysql sql


    【解决方案1】:

    如果我理解正确的话,这 3 个都是相当简单的连接;

    第一个左连接查找所有 FK1=1 的行,并过滤掉所有具有 FK1 和 FK2 反转的匹配对的行;

    SELECT t1.* 
    FROM table1 t1
    LEFT JOIN table1 t2
      ON t1.FK1=t2.FK2 
     AND t1.FK2=t2.FK1
    WHERE t2.PK IS NULL
    AND t1.FK1 = 1;
    

    第二个是同一个查询的反面,而是找到 FK2=1。

    SELECT t1.* 
    FROM table1 t1
    LEFT JOIN table1 t2
      ON t1.FK1=t2.FK2 
     AND t1.FK2=t2.FK1
    WHERE t2.PK IS NULL
    AND t1.FK2 = 1;
    

    第三个只是一个直接的连接,没有特别之处。

    SELECT t1.*
    FROM table1 t1
    JOIN table1 t2
      ON t1.FK2=t2.FK1
     AND t1.FK1=t2.FK2
    WHERE t1.FK1 = 1;
    

    An SQLfiddle for testing.

    【讨论】:

    • 我添加了更多行,一切似乎都是正确的,除了在最后一个查询中您忘记了 t1.FK1 = 1。对吗? sqlfiddle.com/#!2/a0317/1
    • @Sam 是的,你可能是对的,我在理解最后一个描述时遇到了一些麻烦。更新了答案:)
    • @Sam:您没有礼貌地为您正在使用的答案投票吗?你是在谷仓里长大的还是什么?
    猜你喜欢
    • 1970-01-01
    • 2021-12-30
    • 2021-12-21
    • 2018-11-25
    • 2018-01-31
    • 1970-01-01
    相关资源
    最近更新 更多