Tengo una consulta que funciona bien y ofrece el resultado.

SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL)) SubTotal
FROM CustomerData
GROUP BY PartyName, Risk

Datos resultantes:

PartyName   Risk    SubTotal    

A           High    100
B           Med     25
A           Low     30
A           Med     70
B           Low     10

Ahora quiero SUM el total de cada parte y ver los 10 mejores. Me encuentro con 2 problemas al hacerlo:

1. TOP (10) en SUM

Si hago lo siguiente:

SELECT TOP(10) PartyName, SUM(SubTotal) Total
FROM 
    (SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL)) SubTotal
    FROM CustomerData
    GROUP BY PartyName, Risk) AS S
GROUP BY PartyName

Termino con las primeras 10 y no con las 10 sumas más altas.

2. ERROR:

La columna 'S.Risk' no es válida en la lista de selección porque no está contenida ni en una función agregada ni en la cláusula GROUP BY.

Cuando intento lo siguiente:

SELECT TOP(10) PartyName, Risk, SUM(SubTotal) Total
FROM 
    (SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL)) SubTotal
    FROM CustomerData
    GROUP BY PartyName, Risk) AS S
GROUP BY PartyName

Lo que necesito es

PartyName   Risk    SubTotal    Total   

A           High    100         200
B           Med     25          35
A           Low     30          200
A           Med     70          200
B           Low     10          30
1
Sanjna Malpani 15 jun. 2017 a las 16:57

3 respuestas

La mejor respuesta

Problema 1:

Si desea los "10 subtotales más altos", entonces necesita un ORDER BY.

SELECT TOP(10) PartyName, SUM(SubTotal) Total
FROM 
    (SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL)) SubTotal
    FROM CustomerData
    GROUP BY PartyName, Risk) AS S
GROUP BY PartyName
ORDER BY Total DESC

Problema 2:

Esto se vuelve un poco complicado, porque desea GROUP BY tanto PartyName como Risk mientras suma SubTotal, sin embargo, también desea sumar SubTotal por { {X5}} sin enrollarlos.

Una forma de hacer esto sería unir la tabla a otra tabla que sea casi idéntica, sin embargo, la segunda seleccionará Total por Parte (sin tener en cuenta Risk por completo), por lo que que podemos obtener los totales agrupados.

Luego podemos fusionar eso con nuestra consulta inicial ON PartyName para tener una consulta que devuelva tanto los datos acumulados como la repetición de Total por Party.

SELECT TOP(10) s.PartyName, s.Risk, s.SubTotal, s2.Total
FROM 
    (SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL)) SubTotal
    FROM CustomerData
    GROUP BY PartyName, Risk) S
LEFT JOIN
    (SELECT PartyName, SUM(CAST(Amount AS DECIMAL)) Total
    FROM CustomerData
    GROUP BY PartyName) S2 
ON S.PartyName = S2.Partyname
3
Tyler Roper 15 jun. 2017 a las 14:38

En la primera declaración que usó, que con el TOP (10), agregue al final: ORDER BY Total DESC. ¡Eso es todo!:

SELECT TOP(10) PartyName, SUM(SubTotal) Total 
FROM (SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL)) SubTotal 
      FROM CustomerData GROUP BY PartyName, Risk) AS S 
GROUP BY PartyName
ORDER BY Total DESC
0
Rostan 15 jun. 2017 a las 14:18

Si se necesita Riesgo en la consulta externa, GRUPO POR él en la parte inferior.

SELECT TOP(10) PartyName, Risk, SUM(SubTotal) Total
FROM 
    (SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL)) SubTotal
    FROM CustomerData
    GROUP BY PartyName, Risk) AS S
GROUP BY PartyName, Risk

O

SELECT TOP 10 * FROM 
(   SELECT PartyName, Risk, SUM(SubTotal) Total
   FROM 
       (SELECT PartyName, Risk, SUM(CAST(Amount AS DECIMAL))           SubTotal
       FROM CustomerData
       GROUP BY PartyName, Risk) AS S
   GROUP BY PartyName, Risk
)
ORDER BY Total DESC
0
DanielG 15 jun. 2017 a las 14:18