Question

I have the below query and I'm almost (I think) where I need to get it. However, the sum totals in the image below need to be divided by the total of the counts across the rows to display as percentages, not raw counts.

   WITH    cteServices ( [Cnt], OrgName, CatName )
              AS ( SELECT  DISTINCT
                            COUNT(DISTINCT [S].[ServiceId]) AS 'EBPServices' ,
                            [O].[OrganizationName] ,
                            cref.CSAPCategoryName
                   FROM     DVSdmPA.[DM].[Organizations] AS O
                            LEFT JOIN DVSdmPA.[DM].[Programs] AS P ON [O].[OrganizationID] = [P].[OrganizationId]
                            LEFT JOIN DVSdmPA.[DM].[Services] AS S ON [P].[ProgramId] = [S].[ProgramId]
                                                                  AND [S].[FiscalYear] IN (
                                                                  CAST('Jul  1 2012 12:00AM' AS DATETIME) )
                            INNER JOIN DVSdmPA.[MDM_ST].[CountySCALink] AS CSCAL ON [O].[OrganizationId] = [CSCAL].[OrganizationID]
                            INNER JOIN DVSdmPA.[MDM_ST].[SCAReference] AS SCAR ON [CSCAL].[CountyID] = [SCAR].[CountyID]
                            INNER JOIN DVSMDM.GIS.CountyBoundaries CB ON CSCAL.CountyID = CB.CountyId
                            INNER JOIN DVSdmPA.MDM.CSAPCategoryReference cref ON s.CSAPCategoryCode = cref.CSAPCategoryId
                   WHERE    [O].[OrganizationName] NOT IN ( 'National Guard',
                                                            'BDAP Problem Gambling Prevention Pilot',
                                                            'Clarion' )
                            AND s.CSAPCategoryCode IS NOT NULL
                   GROUP BY [O].[OrganizationName] ,
                            cref.CSAPCategoryName
                 )
        SELECT  OrgName ,
                ISNULL(Alternatives, 0) AS Alternatives ,
                ISNULL([Community-Based Process], 0) AS [Community-Based Process] ,
                ISNULL(Education, 0) AS Education ,
                ISNULL(Environmental, 0) AS Environmental ,
                ISNULL([Information Dissemination], 0) AS [Information Dissemination] ,
                ISNULL([Problem Identification and Referral], 0) AS [Problem Identification and Referral]
        FROM    ( SELECT    cnt ,
                            OrgName ,
                            CatName
                  FROM      cteServices
                ) src PIVOT ( SUM(cnt) FOR src.CatName IN ( Alternatives,
                                                            [Community-Based Process],
                                                            Education,
                                                            Environmental,
                                                            [Information Dissemination],
                                                            [Problem Identification and Referral] ) ) AS result
        ORDER BY orgname;

enter image description here

Était-ce utile?

La solution

An easy fix is simply to divide each line by the sum, like this (ugly, but it works):

ISNULL(Alternatives, 0) / (ISNULL(Alternatives, 0) + ISNULL([Community-Based Process], 0) + ISNULL(Education, 0) + ISNULL(Environmental, 0) + ISNULL([Information Dissemination], 0) + ISNULL([Problem Identification and Referral], 0)) as AlternativesPercent

You can also calculate that sum in subquery with the use of WHERE and GROUP BY -- same idea, just a little cleaner.

More importantly, you should consider whether you really want to consolidate the data like this. In the image you provided, what happens when someone asks "Let me see the 5 Environmental's in Bedford" -- you need to run another query. If you go a step further and provide percentages instead of nominal numbers, you'll get even more questions like "what is bigger, 20% of Allegheny or 60% of Blair?". Tools like Excel, or any business intelligence program, can easily work with the raw data and very easily create the same pivot table you're struggling to make here. Additional things like formatting a percentage to exactly 1 decimal in Excel is MUCH easier than doing so in SQL Server. Excel and other tools support drill-through... you could click on the 5 Environmental's in Bedford and they will immediately show up as a list. Thus you get the best of both worlds -- the consolidated pivot table and the raw data. A SQL only requires additional queries to get the underlying data rows.

Consider all your options.

Autres conseils

My suggestion is not the most efficient but should work I think:

setup your final select as a cte (YourFinalSelectAsCte)

add another cte with a select like

,MyCTE as 
(
select 
    OrgName,
    (Alternatives+
    [Community-Based Process]
    Education+
    Environmental+
    [Information Dissemination]+
    [Problem Identification and Referral]) as SummedRow
    from YourFinalSelectAsCte
)

Then just join MyCTE on YourFinalSelectAsCte on OrgName dividing each entry by SummedRow

Again my join on OrgName is not the most efficient, should repeat ServiceId in the previous ctes' selects and use that as a join.

Hope I understood your problem correctly.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top