Question

I'm trying to count many different values in one column in one table, all in one query.

EDIT: Query now works with suggestions by @Red Edit to move the aliases outside of each select and by @dnoeth to move the 'from' line- thanks! I have one more question, which I will add a comment for.

    select 
        m1.mods_in_study,
        (select count(*) 
         from dbo.study as m2 
         where m2.mods_in_study like '%CT%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as CT,
        (select count(*)
         from dbo.study as m3 
         where m3.mods_in_study like '%MR%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as MR,
        (select count(*)
         from dbo.study as m4 
         where m4.mods_in_study like '%CR%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as CR,
        (select count(*)
         from dbo.study as m5 
         where m5.mods_in_study like '%DX%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as DX,
        (select count(*) 
         from dbo.study as m6 
         where m6.mods_in_study like '%US%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as US,
        (select count(*) 
         from dbo.study as m7 
         where m7.mods_in_study like '%PT%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as PT,
        (select count(*)
         from dbo.study as m8 
         where m8.mods_in_study like '%NM%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as NM,
        (select count(*) 
         from dbo.study as m9
         where m9.mods_in_study like '%MG%'
           and study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
           and study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0)) as MG
from dbo.study as m1
group by m1.mods_in_study

Right now, SQL is complaining about the '(' on the 2nd count. Should I be using aliases for this query? I know that a 'union' world work, but won't display correctly in my report as I need a column name for each count.

What am I doing wrong, or is there just a better way of going about this?

Here is what I am expecting the results to be:

CT  MR  CR  DX  US  PT  NM MG
130 39  240 12  45   7  17 121
Was it helpful?

Solution 2

After adding the expected result set it's easier to understand :-)

To get a single row you don't need the FROMor GROUP BY, so simply remove the m1.mods_in_study,and the from dbo.study as m1 group by m1.mods_in_study

But as you always use the same conditions on the same table this can be simplified to

SELECT 
    COUNT(CASE WHEN mods_in_study LIKE '%CT%' THEN 1 END) AS CT, 
    COUNT(CASE WHEN mods_in_study LIKE '%MR%' THEN 1 END) AS MR, 
    ...
FROM dbo.study
WHERE study_datetime >= DATEADD(day, datediff(day, 1, getdate()), 0)
  AND study_datetime < DATEADD(day, datediff(day, 0, getdate()), 0))    

MarkD's solution is quite similar...

OTHER TIPS

Not having a terminal at hand where I can test MSSQL but reading through the query it would seem like you are just missing a comma.

If this is what you are after, I'd advise to code against the following pattern. It is typically more efficient that the correlated sub-queries and a better practice;

SELECT   mods_in_study
        ,CT =   SUM (   CASE 
                            WHEN mods_in_study LIKE '%CT%' 
                            AND  study_datetime >= DATEADD(DAY ,DATEDIFF(DAY ,1 ,GETDATE()) ,0) 
                            AND  study_datetime < DATEADD(DAY ,DATEDIFF(DAY ,0 ,GETDATE()) ,0)
                            THEN 1
                            ELSE 0
                        END
                    )
        ,MR =   SUM (   CASE 
                            WHEN mods_in_study LIKE '%MR%' 
                            AND  study_datetime >= DATEADD(DAY ,DATEDIFF(DAY ,1 ,GETDATE()) ,0) 
                            AND  study_datetime < DATEADD(DAY ,DATEDIFF(DAY ,0 ,GETDATE()) ,0)
                            THEN 1
                            ELSE 0
                        END
                    )
        --  Etc...
FROM   dbo.study
GROUP BY mods_in_study
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top