子表中的SQL计数

时间:2017-02-21 11:54:12

标签: sql sql-server-2012

我想从子表中计算一些列。我的表结构如下:

+---+----------+--------+
| Pid | Name   |Surname |
+---+----------+--------+
| 1   | Per A  | D      |
| 2   | Per B  | E      |
| 3   | Per C  | F      
+----+---------+--------+

童车

+---+---------+-------------------+------------+-----+
| Cid | CName          | School   | Sex        | Pid |
+---+---------+-------------------+------------+-----+
| 1   | John           | High     |    Man     | 1   |
| 2   | Alice          | Primary  |    Woman   | 2   |
| 3   | Mel            | High     |    Man     | 3   |
| 4   | Angelina       | High     |    Woman   | 2   |
+----+---------+------------------+------------+-----+

所以我要输出

+---+----------+------+---------+--------+---+--------------+
| Pid| PerName | High | Primary | Woman  | Man | ChildCount | 
+---+----------+------+---------+--------+-----+------------+
| 1  | Per A   | 1    | 0       | 0      | 1   | 1          |
| 2  | Per B   | 1    | 1       | 2      | 0   | 2          |
| 3  | Per C   | 1    | 0       | 0      | 1   | 1          |
+----+---------+------+---------+--------+-----+------------+

如何获得此输出?

我尝试这种方法,但我有更多这样的列来计算属于Child表。所以我的查询结果很慢。

select Pid,Name,Surname,
  (select count(*) from Childs where Persons.Pid=Childs.Pid) ChildCount, 
  (select count(*) from Childs where Persons.Pid=Childs.Pid and School='Primary') Primary 
from Persons

2 个答案:

答案 0 :(得分:2)

您可以使用join和条件聚合:

执行此操作
select p.Pid, p.Name,
       sum(case when c.school = 'High' then 1 else 0 end) as high,
       sum(case when c.school = 'Primary' then 1 else 0 end) as primary,
       sum(case when c.sex = 'Man' then 1 else 0 end) as Man,
       sum(case when c.sex = 'Woman' then 1 else 0 end) as Woman,
       count(*) as ChildCount
from persons p left join
     childs c
     on p.pid = c.pid
group by p.Pid, p.Name;

答案 1 :(得分:0)

试试这个:

select Pid,Name,Surname,
ifNull((select count(*) from Childs where Persons.Pid=Childs.Pid),0) ChildCount,
ifNull((select count(*) from Childs where Persons.Pid=Childs.Pid AND School='High' GROUP By Childs.Pid),0) High,
ifNull((select count(*) from Childs where Persons.Pid=Childs.Pid AND School='Primary' GROUP By Childs.Pid),0) 'primary',
ifNull((select count(*) from Childs where Persons.Pid=Childs.Pid AND Sex='Woman' GROUP By Childs.Pid),0) Woman,
ifNull((select count(*) from Childs where Persons.Pid=Childs.Pid AND Sex='Man' GROUP By Childs.Pid),0) Man

from Persons;