2012-04-27 67 views
4

我有一个消息系统,它作为消息系统和聊天系统加倍出来,这些系统通过称为源的字段进行区分。选择所有匹配的两个字段,并用这两个字段与mysql分组

我有消息部分排序,并在聊天部分然而正确分组它不是分组这些相应的,请参阅下面我的SQL:

SELECT * 
FROM messages 
WHERE (senderID = "1" OR receiverID = "1") 
AND source = "1" 
GROUP BY receiverID, senderID 
ORDER BY addedDate DESC LIMIT 10 

所以我期待的结果是每场比赛只有一个,即每个对话一个

然而,由于某种原因,我得到两个。

在此先感谢

+1

你能提供一些样本数据吗? – mellamokb 2012-04-27 12:38:46

+0

您可以提供表格数据 – 2012-04-27 12:49:24

+0

在对行进行分组时,您必须在SELECT语句中指定列。 – 2012-04-27 12:49:31

回答

2

你可能会得到每个聊天两个答案,因为你将有每个人在两个位置

ChatID Sender Receiver 
1  1  2 
2  2  1 
3  1  2 
4  2  1 

So, you'll have a record grouped by 
Sender/Receiver 
1  2   and 
2  1 

我想你正在寻找的是不同的人在谈话,其中以上,应考虑“一对一聊天”的位置无关,他们都在为了解决这个问题,我会做这样的事情......

select 
     PreQuery.*, 
     m2.Message, 
     m2.SenderID, 
     m2.ReceiverID 
    from 
     (SELECT 
       if(m.senderID < m.receiverID, m.senderID, m.receiverID) as Person1, 
       if(m.senderID < m.receiverID, m.receiverID, m.senderID) as Person2, 
       max(m.ID) as LastMessageIDPerChat, 
       max(m.AddedDate) as LastMessageDate 
      FROM 
       messages m 
      WHERE 
        m.Source = "1" 
       AND "1" IN (SenderID, ReceiverID) 
      GROUP BY 
       Person1, 
       Person2 
      ORDER BY 
       m.AddedDate DESC 
      LIMIT 10) PreQuery 

     JOIN Messages m2 
      on PreQuery.LastMessageIDPerChat = m2.ID 

这将确保无论哪个ID是将低ALWA ys位于第一位置,并且无论哪个人的身份证号码更高,总是处于第二位置以防止上述虚假重复。

另请注意...... GROUP BY通常期望所有非group by字段都与某个聚合关联,否则,它只会抓取具有合格条件的记录的第一个实例。所以,如果你想在不同的日子对话一样的人,你会希望通过这样它可能需要添加“AddedDate”之类的......

Person1 Person2 on 4/20 
Person1 Person3 on 4/20 
Person3 Person4 on 4/20 
Person1 Person2 on 4/18 
Person1 Person5 on 4/17 
Person3 Person4 on 4/15 

要得到谁发出最后的状态,我必须为每个对话包装配对人的查询并获得该对话的最后一个ID。然后,将其重新加回到该ID​​上的消息(如果ID实际上是消息表的主键ID,则根据需要进行调整)。从加入中,我可以获得对话的最后一条消息以及发件人ID和接收者ID是用于该交易的人(以及您希望从现在的别名“m2”参考获得的任何其他数据)。

+0

这正是我想要做的,但是看着senderID,发件人ID是什么大于接收者ID? – 2012-04-27 14:06:31

+0

@AndréFigueira,这就是为什么IF()检查发送者与接收者相比。如果发件人较大,则接收人成为第一人称位置,发件人成为第二人称位置。 – DRapp 2012-04-27 14:14:28

+0

我看得好,但那么这意味着较低的ID将永远是接收器的权利? – 2012-04-27 15:01:28

0

检查了出来。

SELECT 
    receiverID, 
    senderID, 
    MAX(addedDate) as maxAddedDate 
FROM messages 
WHERE (senderID = 1 OR receiverID = 1) AND source = 1 
GROUP BY receiverID, senderID 
ORDER BY addedDate DESC 

您还没有提到任何字段组的聚合。

如果你有多个记录根据字段的任何组,然后会发生什么?

你应该有总和,计数,...

+0

好,如果它匹配一个谈话,例如用户ID可以是接收者或发件人,并且可以是发件人或接收者的号码 – 2012-04-27 13:00:35

1

你确定你的ID不是整数吗?

SELECT 
    receiverID, 
    senderID, 
    MAX(addedDate) as maxAddedDate 
FROM 
    messages 
WHERE 
    ( 
     senderID = 1 
     OR receiverID = 1 
    ) 
    AND source = 1 
GROUP BY 
    receiverID, 
    senderID 
ORDER BY 
    addedDate DESC 
LIMIT 10 
+0

这还没有做 – 2012-04-27 12:58:05

+0

那么结果是什么? – 2012-04-27 12:58:47

+0

完全一样,它们都是整数。 – 2012-04-27 13:01:25

相关问题