标题有点尴尬,但我会尽力解释我想要完成的事情。
我有一个名为 Users
的表和另一个名为 Friends
的表。
Users
表的抽象结构是:
+----+------+----------+----------+
| ID | Name | Username | Password |
+----+------+----------+----------+
Friends
表的抽象结构如下:
+----+--------+----------+--------+
| ID | UserID | FriendID | Hidden |
+----+--------+----------+--------+
其中 UserID
是发送好友请求的用户的 ID,FriendID
是请求的接收者。如果收件人选择隐藏请求,则隐藏列的值为 1。
我想将这一切压缩为一个查询,到目前为止,我有两个单独的查询,它们使用 LEFT JOIN
或 RIGHT JOIN
。
查找已发送的请求和当前好友:
SELECT
*,
CASE
WHEN C.ID IS Null THEN "Request Sent"
ELSE "Friends"
END AS Status
FROM
(SELECT DISTINCT
A.ID, A.Name, E.Hidden
FROM
Users A
INNER JOIN
Friends E ON A.ID = E.UserID
WHERE
A.ID in (SELECT UserID
FROM Friends
WHERE FriendID = "1" AND Deleted='No')) C
RIGHT JOIN
(SELECT DISTINCT
B.ID, B.Name, F.Hidden
FROM
Users B
INNER JOIN
Friends F ON B.ID = F.FriendID
WHERE
B.ID in (SELECT FriendID
FROM Friends
WHERE UserID = "1" AND Deleted = 'No')) D ON C.ID = D.ID
关于收到的好友请求和当前好友:
SELECT *, CASE WHEN D.ID IS Null THEN "Wants to be your friend" ELSE "Friends" END AS Status FROM
(SELECT DISTINCT
A.ID, A.Name, E.Hidden
FROM
Users A INNER JOIN Friends E ON A.ID=E.UserID
WHERE
A.ID in (SELECT UserID FROM Friends WHERE FriendID = "1" AND Deleted='No')) C
LEFT JOIN
(SELECT DISTINCT
B.ID, B.Name, F.Hidden
FROM
Users B INNER JOIN Friends F ON B.ID=F.FriendID
WHERE
B.ID in (SELECT FriendID FROM Friends WHERE UserID = "1" AND Deleted='No')) D
ON C.ID=D.ID
如果我没有解释我需要什么,下面的维恩图可能是一个重要的说明性插入。
请注意,为了构建查询,我选择了所有列,但最后我只需要 friend 姓名和 ID。
最佳答案
在两个查询之间执行union all
或union distinct
这将在一个表中返回所有结果。
SELECT *, D.ID, CASE WHEN D.ID IS Null THEN "Wants to be your friend" ELSE "Friends" END AS Status FROM
(SELECT DISTINCT
A.ID, A.Name, E.Hidden
FROM
Users A INNER JOIN Friends E ON A.ID=E.UserID
WHERE
A.ID in (SELECT UserID FROM Friends WHERE FriendID = "1" AND Deleted='No')) C
LEFT JOIN
(SELECT DISTINCT
B.ID, B.Name, F.Hidden
FROM
Users B INNER JOIN Friends F ON B.ID=F.FriendID
WHERE
B.ID in (SELECT FriendID FROM Friends WHERE UserID = "1" AND Deleted='No')) D
ON C.ID=D.ID
union all
SELECT *, D.ID, CASE WHEN C.ID IS Null THEN "Request Sent" ELSE "Friends" END AS Status FROM
(SELECT DISTINCT
A.ID, A.Name, E.Hidden
FROM
Users A INNER JOIN Friends E ON A.ID=E.UserID
WHERE
A.ID in (SELECT UserID FROM Friends WHERE FriendID = "1" AND Deleted='No')) C
RIGHT JOIN
(SELECT DISTINCT
B.ID, B.Name, F.Hidden
FROM
Users B INNER JOIN Friends F ON B.ID=F.FriendID
WHERE
B.ID in (SELECT FriendID FROM Friends WHERE UserID = "1" AND Deleted='No')) D
ON C.ID=D.ID
关于同表中记录的 MySQL 连接类型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23767437/