查找具有两列唯一组合的所有行

时间:2014-03-29 08:54:06

标签: sql ruby-on-rails postgresql duplicates aggregate

我有这张表messages;

sender_id    recipient_id
1            2
1            3
1            3
2            1
3            1
2            3

我希望选择以下行:

  1. sender_idreceiver_id = current_user.id
  2. 其他字段应该是唯一的。
  3. 即。我想从sender_id = 2recipient_id = 2的表中选择唯一的,我需要这个结果:

    sender_id    recipient_id
    2            1
    2            3
    

    怎么做?
    为什么?因为我希望建立一个类似于Facebook的收件箱,其中汇总了已发送和已接收的邮件,此查询是目前的瓶颈。

    我正在使用rails 3.2和Postgres 9.3。

2 个答案:

答案 0 :(得分:5)

SELECT sender_id AS user_id, recipient_id AS other_user_id
FROM   messages
WHERE  sender_id = $current_user_id

UNION
SELECT recipient_id, sender_id
FROM   messages
WHERE  recipient_id = $current_user_id
-- ORDER BY 1, 2  -- optional

UNION(不是UNION ALL)从结果中删除重复项,使DISTINCT不必要。 您可能希望在末尾添加ORDER BY以进行排序输出。

假设一个大型表具有相对较少的符合条件的行,则两个btree索引通常可以提供最佳性能。一个带有前导或仅sender_id,另一个带前导或仅recipient_id

(sender_id, receiver_id)上的单个multicolumn index或反之亦然,但通常较慢。参见:

答案 1 :(得分:2)

使用ANSI SQL:

SELECT DISTINCT sender_id, reciepient_id
FROM messages
WHERE (sender_id = current_user.id or reciepient_id = current_user.id)