2012-03-05 31 views
20

Estoy tratando de perfeccionar una consulta que actualmente estoy usando:MySQL - RECUENTO condicional con GROUP BY

SELECT `puid`, 
     COUNT(DISTINCT `droid_v`) AS DROID, 
     COUNT(DISTINCT `sig_v`) AS sig, 
     SUM(NoExt) AS hits 
     FROM temp 
     GROUP BY `puid` 

y tengo que conseguir que sólo cuentan droid_v donde droid_V es mayor que 0. ¿Es posible condicionar el recuento de esta manera? Por el momento, está contando valores cero como contables, y realmente no puedo cambiar los ceros a valores null.

No necesito saber el valor de recuento para droid_V = 0, solo necesito contarlo si tiene un número mayor que 0. Ese número siempre será 0, 1, 2, 3 o 4.


que he intentado:

SELECT `puid`, 
    COUNT(DISTINCT CASE WHEN `droid_v` > 0 THEN 1 END) AS DROID, 
    COUNT(DISTINCT `sig_v`) AS sig, 
    SUM(`NoExt`) AS hits 
    FROM temp 
    GROUP BY `puid` 

Pero esto da un resultado binario (0 o 1) no es el recuento que estoy esperando.

ejemplo de salida =

puid   DROID sig  hits 
No PUID   1  1  252 
x-fmt/92  1  5  1008 

salida anticipada:

puid   DROID sig  hits 
No PUID   1  1  252 
x-fmt/92  3  5  1008 

datos de la muestra:

id;puid;droid_v;sig_v;speed;Ext;NoExt;tally 


1;"No PUID";"3";"v13";"SLOW";"0";"63";"63" 
2;"x-fmt/92";"3";"v13";"SLOW";"63";"0";"63" 
3;"x-fmt/92";"3";"v37";"SLOW";"63";"63";"126" 
4;"x-fmt/92";"3";"v45";"SLOW";"63";"63";"126" 
5;"x-fmt/92";"3";"v49";"SLOW";"63";"63";"126" 
6;"x-fmt/92";"3";"v50";"SLOW";"63";"63";"126" 
7;"x-fmt/92";"5";"v13";"SLOW";"63";"0";"63" 
8;"No PUID";"5";"v13";"SLOW";"0";"63";"63" 
9;"x-fmt/92";"5";"v37";"SLOW";"63";"63";"126" 
10;"x-fmt/92";"5";"v45";"SLOW";"63";"63";"126" 
11;"x-fmt/92";"5";"v49";"SLOW";"63";"63";"126" 
12;"x-fmt/92";"5";"v50";"SLOW";"63";"63";"126" 
13;"No PUID";"6";"v13";"FAST";"0";"63";"63" 
14;"x-fmt/92";"6";"v13";"SLOW";"63";"0";"63" 
15;"No PUID";"6";"v13";"SLOW";"0";"63";"63" 
16;"x-fmt/92";"6";"v13";"FAST";"63";"0";"63" 
17;"x-fmt/92";"6";"v37";"SLOW";"63";"63";"126" 
18;"x-fmt/92";"6";"v37";"FAST";"63";"63";"126" 
19;"x-fmt/92";"6";"v45";"FAST";"63";"63";"126" 
20;"x-fmt/92";"6";"v45";"SLOW";"63";"63";"126" 
21;"x-fmt/92";"6";"v49";"FAST";"63";"63";"126" 
22;"x-fmt/92";"6";"v49";"SLOW";"63";"63";"126" 
23;"x-fmt/92";"6";"v50";"FAST";"63";"63";"126" 
24;"x-fmt/92";"6";"v50";"SLOW";"63";"63";"126" 
+0

¿puedes agregar una cláusula 'WHERE'? –

+0

del ejemplo que proporcionó, ¿cuál es su resultado esperado? –

Respuesta

26

Si droid_v solo puede ser 0, 1, 2, 3 o 4, entonces COUNT (DISTINCT) nunca devolverá más de 5, ya que solo hay cinco valores posibles. ¿Es eso lo que quieres? Si es así, entonces prueba este:

SELECT puid, COUNT(DISTINCT CASE WHEN droid_v > 0 THEN droid_v ELSE 0 END) - 1 AS droid /* -1 for the case where droid_v is 0 */ 
    , COUNT(DISTINCT sig_v) AS sig 
    , SUM(NoExt) AS hits 

Actualización: Vaya, lo siento, lo anterior no es del todo bien ya que puede no ser un cero. Debería ser:

SELECT puid, COUNT(DISTINCT CASE WHEN droid_v > 0 THEN droid_v END) AS droid 

Si, por el contrario, desea un recuento de todas las filas donde droid_v> 0, entonces yo creo que usted quiere esto:

SELECT puid, SUM(CASE WHEN droid_v > 0 THEN 1 ELSE 0 END) AS droid 
    , COUNT(DISTINCT sig_v) AS sig 
    , SUM(NoExt) AS hits 

Espero que esto ayude.

+0

Esa es la única: estaba hurgando en ello antes de su cambio, y tratando de descubrir qué estaba mal. Tienes razón, no puede ser cero. Gracias por tu tiempo. – Jay

7
SELECT 
    `puid`, 
    COUNT(DISTINCT CASE WHEN `droid_v` > 0 THEN `droid_v` END) AS DROID, 
    COUNT(DISTINCT `sig_v`) AS sig, 
    SUM(NoExt) AS hits 
+0

Hola, gracias por la sugerencia, he editado la pregunta para responder a tu idea. – Jay

+0

Mi respuesta inicial fue incorrecta a pesar de su pregunta clara. Ver respuesta revisada. –

+0

Eso funciona como se esperaba. Gracias por la revisión. – Jay

1

añadir esto a la consulta

WHERE droid_v > 0 
+0

Gracias echando un vistazo, pero eso realmente no funcionó. – Jay

3

Esta es la solución más simple que puedo pensar:

SELECT puid, 
SUM(droid_v > 0) AS DROID, 
COUNT(DISTINCT sig_v) AS sig, 
SUM(`NoExt`) AS hits 
FROM t 
GROUP BY puid 

Sin embargo, no está claro si se desea contar el distintivo o no.Si desea contar los valores distintos a continuación:

SELECT puid, 
COUNT(if(droid_v > 0, droid_v, null)) AS DROID, 
COUNT(DISTINCT sig_v) AS sig, 
SUM(`NoExt`) AS hits 
FROM t 
GROUP BY puid 
+0

Gracias por echar un vistazo, está cerca, pero pierde la función distinta que necesito (lo siento si no lo dejé claro) – Jay

5

sólo tiene que utilizar una suma

por lo que si desea agrupar algo que mira esto

select city, sum(case when gender = 'male' then 1 else 0 end) as male, 
sum(case when gender = 'female' then 1 else 0 end) as female 
from person 
group by city 

simple como esto: D