如何在一个SQL查询中基于不同的参数获得多个计数?

时间:2018-12-10 16:52:03

标签: sql sql-server

我有一张桌子,上面有多个亲戚的医疗记录。我正在尝试按相对程度对癌症诊断进行计数。

CREATE TABLE Relatives
(person varchar(9), 
 relative varchar(12), 
 degree int, 
 relativeID varchar(9),
 age int, 
 CancerDiagnosis varchar(2))

INSERT INTO RELATIVES (person, relative, degree, relativeid, age, cancerdiagnosis)
VALUES ('12345678','aunt','2','54876','36','Y'),
       ('12345678','aunt','2','54876','43','Y'),
       ('12345678','cousin','3','213786','39','N'),
       ('12345678','daughter','1','128756','15','Y'),
       ('12345678','daughter','1','128756','21','Y'),
       ('12345678','daughter','1','128756','12','N'),
       ('12345678','father','1','867578','64','Y'), 
       ('98765432','cousin','3','987645','39','Y'),
       ('98765432','cousin','3','987645','40','Y'),
       ('98765432','sibling','1','123744','22','N'),
       ('98765432','mother','1','876418','64','Y'),
       ('98765432','mother','1','876418','65','Y'),

我希望得到结果:

  person    fdr_cancer    sdr_cancer   tdr_cancer 
12345678      2              1           0
98765432      1              0           1

这是我的查询:

SELECT person, 
SUM(CASE WHEN cancerdiagnosis = 'y' AND degree = 1 THEN 1 ELSE 0 END) AS 
FDR_Cancer,
SUM(CASE WHEN cancerdiagnosis = 'y' AND degree = 2 THEN 1 ELSE 0 END) AS 
SDR_Cancer,
sum(CASE WHEN cancerdiagnosis = 'y' AND degree = 3 THEN 1 ELSE 0 END) AS 
TDR_Cancer
FROM Relatives 
GROUP BY person

如何获取此数据以按相对ID,程度和诊断来计数不同的行?

3 个答案:

答案 0 :(得分:0)

如果我的理解正确,那么您需要有条件的count(distinct)

SELECT person, 
       COUNT(DISTINCT CASE WHEN cancerdiagnosis = 'y' AND degree = 1 THEN relativeid END) AS FDR_Cancer,
       COUNT(DISTINCT CASE WHEN cancerdiagnosis = 'y' AND degree = 2 THEN relativeid END) AS SDR_Cancer,
       COUNT(DISTINCT CASE WHEN cancerdiagnosis = 'y' AND degree = 3 THEN relativeid END) AS TDR_Cancer
FROM Relatives 
GROUP BY person;

答案 1 :(得分:0)

您可以在聚合之前将DISTINCT 应用于,而不是三个COUNT DISTINCT,

with cte as 
 ( select distinct 
      person, degree, relativeid, cancerdiagnosis
   from Relatives 
 )
SELECT person, 
   SUM(CASE WHEN cancerdiagnosis = 'y' AND degree = 1 THEN 1 ELSE 0 END) AS FDR_Cancer,
   SUM(CASE WHEN cancerdiagnosis = 'y' AND degree = 2 THEN 1 ELSE 0 END) AS SDR_Cancer,
   sum(CASE WHEN cancerdiagnosis = 'y' AND degree = 3 THEN 1 ELSE 0 END) AS TDR_Cancer
FROM cte 
GROUP BY person

有可能将cancerdiagnosis = 'y'作为WHERE条件转移到CTE中(但随后将省略对 all 行的诊断为N的人):

with cte as 
 ( select distinct 
      person, degree, relativeid
   from Relatives 
   where cancerdiagnosis = 'y'
 )
SELECT person, 
   SUM(CASE WHEN degree = 1 THEN 1 ELSE 0 END) AS FDR_Cancer,
   SUM(CASE WHEN degree = 2 THEN 1 ELSE 0 END) AS SDR_Cancer,
   sum(CASE WHEN degree = 3 THEN 1 ELSE 0 END) AS TDR_Cancer
FROM cte 
GROUP BY person

答案 2 :(得分:0)

以前的答案更容易理解,但是另一种选择是使用PIVOT

SELECT 
    person
    ,[1] AS FDR_Cancer
    ,[2] AS SDR_Cancer
    ,[3] AS TDR_Cancer
FROM 
    (
        SELECT DISTINCT 
            person
            ,relativeid
            ,degree
            ,CancerDiagnosis
        FROM Relatives
    ) ps
PIVOT 
    (
        COUNT(relativeid) FOR degree IN ([1],[2],[3])
    ) AS pvt
WHERE 
    pvt.CancerDiagnosis = 'Y'