2017-09-03 50 views
0

我有2台这样的记录:排除存在于另一个表

emails: 
emailID int(10) auto_increment, memberID int(10), emailData text, and so on 

members: 
memberID int(10) auto_increment, user_name char(40), password char(50), and so on 

我的查询是这样的:

select 
emails.emailID, emails.emailData, 
members.memberID, members.user_name 
from emails, members where 
emails.memberID = members.memberID 

现在我已经添加了两个更多的表像这样:

blocked: 
id int(10) auto_increment, memberID int(10), blocked_memberID int(10) 

markedAsRead: 
id int(10) auto_increment, memberID int(10), emailID int(10) 

我想修改我的原始查询,以便它排除memberID这是blocked.blocked_memberID也是排除emailID哪些在markedAsRead.emailID

我该怎么做?

+0

重复https://stackoverflow.com/questions/4560471/how-to-exclude-rows-that-dont-join-with-another-table – Dmitry

+1

可能的复制[如何排除不与另一个表连接的行?](https://stackoverflow.com/questions/4560471/how-to-exclude-rows-that-dont-join-with-another-table) – Dmitry

回答

1

您可以使用NOT EXISTS

SELECT .... 
FROM .... 
WHERE ..... // Replace the dots with Your Query 
    AND NOT EXISTS(SELECT 1 FROM blocked 
       WHERE emails.memberID = blocked.memberID) 
    AND NOT EXISTS(SELECT 1 FROM markedAsRead 
       WHERE emails.emailID = markedAsRead.emailID) 

你也可以查找的LEFT JOINSNOT IN排除不存在于一个特定的表中的记录。

编辑:通常EXISTS()LEFTJOIN有类似performaces,有时它甚至可以执行比加入更好。

LEFT JOIN sulotion:中

SELECT ... 
FROM ... 
LEFT JOIN blocked 
ON(WHERE emails.memberID = blocked.memberID) 
LEFT JOIN markedAsRead 
ON(emails.emailID = markedAsRead.emailID) 
WHERE ... 
AND blocked.memberID IS NULL 
AND markedAsRead.emailID IS NULL 
+0

嗨,在您发布的不存在的链接中,它表示将为每个匹配主查询的记录运行子查询。如果表格变大,那么这会成为一个主要问题,特别是如果次表格也很大?如果是这样,你是否也可以发表你提到的左连接的例子?谢谢 –

+0

请参阅编辑。只要您的表格索引正确,两者之间不应该存在问题或主要区别,但我还包含左连接解决方​​案。 – sagi

+0

谢谢sooo多:)像你提到的,如果性能是类似的,所以我会去用不存在的方法。这似乎更容易理解。再次感谢 :) –

相关问题