2010-04-03 59 views
12

我有一个简单的一对多关系。我只想在父母至少有一个孩子时从父母中选择行。所以,如果没有孩子,那么父行不会返回结果集中。如何仅在至少有一个孩子的情况下选择父行?

例如,

Parent: 
+--+---------+ 
|id| text | 
+--+---------+ 
| 1| Blah | 
| 2| Blah2 | 
| 3| Blah3 | 
+--+---------+ 

Children 
+--+------+-------+ 
|id|parent| other | 
+--+------+-------+ 
| 1| 1 | blah | 
| 2| 1 | blah2 | 
| 3| 2 | blah3 | 
+--+------+-------+ 

我想要的结果是:

+----+------+ 
|p.id|p.text| 
+----+------+ 
| 1 | Blah | 
| 2 | Blah2| 
+----+------+ 

回答

15

您可以使用EXISTS做到这一点,是这样的:

SELECT * 
FROM Parent p 
WHERE EXISTS (SELECT 1 
       FROM Chilren c 
       WHERE c.Parent = p.id) 

或使用IN这样的:

SELECT * 
FROM Parent p 
WHERE p.id IN (SELECT c.Parent 
       FROM Chilren c) 
+2

我没有测试过,但我猜测这是不是加入慢。 – Hogan 2010-04-03 16:22:49

+3

@霍根 - 存在它是最快的方法。优化器将为空检查的外连接执行相同的执行计划......这将**作为**快速,但存在永远不会变慢。 – 2010-04-03 16:24:02

+0

整洁。谢谢@尼克。对于mysql,ms sql和oracle这是真的吗? – Hogan 2010-04-04 16:35:23

1
SELECT p.* 
FROM Parent p 
WHERE EXISTS (SELECT 'X' FROM Children c WHERE c.parent = p.id); 
2
Select p.id, p.text 
from Parent p 
inner join Children c on p.id = c.parent 
group by p.id, p.text 
12

inner join只返回匹配两个表的行:

select distinct p.* 
from Parent p 
inner join Children c on c.parent = p.id 
+1

在我看来,这是实现这个目标最直接的方法,应该是被接受的答案。 – adriandz 2013-08-14 17:35:40

相关问题