0

我正在尝试创建一个查询,但我不知道如何。

我有三个表chatchat_useruser

就像是:

 ---------      ------------------------       ------------------
|  chat   |    |        chat_user       |     |       user       |
 ---------      ------------------------       ------------------
| id |  1 |    | id | chat_id | user_id |     | id | external_id | 
 ---- ----      ---- --------- ---------       ---- -------------
               | 1  |    1    |    1    |     |  1 |     111     |
               | 2  |    1    |    2    |     |  2 |     222     |
                ---- --------- ---------       ---- -------------

user我需要为两个选择一个 chat.id。在上面的示例中,用户 111 和 222 共享chat.id1。我需要的是在搜索111 和 222chat.id时仅获得一次选择结果 1(如上例) 。external_id

我在这里找到了一些答案,但它们并没有太大帮助......我总是得到其他 chat.id 值。

如果您需要任何额外的解释,我就在这里回答。

提前致谢!

4

2 回答 2

4

这实际上是“set-within-sets”查询的一个示例:您正在询问给定聊天的用户集是否包含某些用户。我喜欢用聚合和子句来解决这样的问题having,因为这是一种非常通用的方法。

这是查询:

select c.*
from chat_user cu join
     user u
     on cu.user_id = u.id join
     chat c
     on cu.chat_id = c.id
group by cu.chat_id
having sum(u.external_id = '111') > 0 and
       sum(u.external_id = '222') > 0

这是通过聊天汇总的chat_user。该having子句中的第一个条件是:“用户 111 是否存在?”。第二个说:“用户 222 在场吗?” 仅返回包含两个用户示例的聊天 ID。

于 2013-06-05T23:28:27.467 回答
2
SELECT id FROM chat AS c
INNER JOIN chat_user AS cu1 ON c.id = cu1.chat_id
INNER JOIN chat_user AS cu2 ON c.id = cu2.chat_id AND cu1.id < cu2.id
INNER JOIN user AS u1 ON u1.id = cu1.user_id
INNER JOIN user AS u2 ON u2.id = cu2.user_id
WHERE u1.external_id = 111
AND u2.external_id = 222

AND cu1.id < cu2.id部分强制将chat_userwith id1 连接为 escu1并将chat_userwith id2 连接为cu2。这消除了chat_userwith id2 连接为 ascu1chat_userwith id1 连接为的记录cu2。我的猜测是你在尝试中省略了这个子句,这导致了重复。

于 2013-06-05T23:13:27.283 回答