2008-08-31 146 views
11

我有三个表:页,附件,页附件SQL查询,计数为0计数

我有这样的数据:

page 
ID NAME 
1  first page 
2  second page 
3  third page 
4  fourth page 

attachment 
ID NAME 
1  foo.word 
2  test.xsl 
3  mm.ppt 

page-attachment 
ID PAGE-ID ATTACHMENT-ID 
1  2   1 
2  2   2 
3  3   3 

我想获得每页附件的数量也是当这个数字是0。我曾尝试用:

select page.name, count(page-attachment.id) as attachmentsnumber 
from page 
    inner join page-attachment on page.id=page-id 
group by page.id 

我得到这样的输出:

NAME  ATTACHMENTSNUMBER 
second page 2 
third page 1 

我想获得这个输出:

NAME  ATTACHMENTSNUMBER 
first page 0 
second page 2 
third page 1 
fourth page 0 

如何得到0的一部分?

回答

25

将您的“内连接”更改为“左外连接”,这意味着“即使在右侧没有匹配的行,也可以让我连接左侧的所有行。

select page.name, count(page-attachment.id) as attachmentsnumber 
from page 
    left outer join page-attachment on page.id=page-id 
group by page.name 
+0

正如David B.提到这个查询不会运行。将组更改为'group by page.name' – edosoft 2009-01-21 13:04:07

1

您想要一个左连接而不是内连接,因为这样可以使记录不存在。

8

这是另一种使用子查询的解决方案。

​​
+0

谢谢!适合我! – tienbuiDE 2014-11-15 18:19:39

2

根据数据库的不同,对于速度,可以使用UNION命令。

SQL比较长,但是,根据数据库的不同,它通过分开“统计存在的事物”和“计算不存在的事物”来加快速度。

(
select page.name, count(page-attachment.id) as attachmentsnumber 
from page 
inner join page-attachment on page.id=page-id 
group by page.id 
) 
UNION 
(
select page.name, 0 as attachmentsnumber 
from page 
where page.id not in (
    select page-id from page-attachment) 
) 

我需要这个解决方案的数据库有超过一百万个附件的20页。 UNION使它在13秒内运行,而不是这么长时间,我感到无聊,并尝试另一种方式(在我杀死外连接和子查询方法之前60秒以上的地方)。

0

使用此:

SELECT p.name,(
    SELECT COUNT(*) FROM [page-attachment] pa WHERE pa.[PAGE-ID] = p.id) as attachmentsnumber 
FROM page p