2011-03-25 30 views
5

Tengo una vista (muchas uniones) que muestra datos ordenados por una fecha ASC. Funciona como se esperabaGROUP_CONCAT cambiar GROUP BY orden

una salida similar a:

ID date   tag1 other_data 
1 25-03-2011 blue fff <= 
1 26-03-2011 red ggg 
1 27-03-2011 pink yyy 
2 25-03-2011 red yyy <= 
2 26-03-2011 orange rrr 

Si aplico un GROUP BY ID. Para las otras columnas, MySQL genera la primera fila encontrada de cada ID. Lo leí en algún lugar de los documentos te.

SELECT * FROM `myVIEW` 
GROUP BY `ID` 
    ID date   tag1 other_data 
    1 25-03-2011 blue fff <= 
    2 25-03-2011 red yyy <= 

Ahora vamos a añadir un GROUP_CONCAT (tags1)

SELECT *,CONCAT_GROUP(`tag1`) AS `tags` 
FROM `myVIEW` 
GROUP BY `ID` 

Desde aplico el CONCAT_GROUP los resultados se extraña. Yo estaba esperando:

ID date   tag1 other_data tags 
1 25-03-2011 blue fff   blue,red,pink 
2 25-03-2011 red yyy   red,orange 

La consulta está regresando, por ejemplo:

ID date   tag1 other_data tags 
1 26-03-2011 red ggg   blue,red,pink 
2 25-03-2011 red yyy   red,orange 

Parece que GROUP_CONCAT ya no conserva el orden de visualización. ¿Esto es normal?

Respuesta

1

Esto se debe a que mysql no garantiza qué filas exactas serán devueltas para los campos que no se usan en las funciones de agregación o no se usaron para agrupar.

Y para ser claros los rdbms "maduros" (como postgre, sql server, oracle) no permiten especificar * en GROUP BY (o cualquier campo sin agregación o no especificado en GROUP BY) - y es genial " limitación".

5

Parece GROUP_CONCAT ya no conserva la orden VER. ¿Esto es normal?

Sí, es normal.

No debe confiar, nunca, en el orden en el que se devuelven los campos desagrupados y no agrupados.

GROUP_CONCAT tiene su propia cláusula ORDER BY que el optimizador tiene en cuenta y puede cambiar el orden en que se procesan los registros.

Para volver al primer registro, junto con GROUP_CONCAT, utilice esto:

SELECT m.*, gc 
FROM (
     SELECT id, MIN(date) AS mindate, GROUP_CONCAT(tags) AS gc 
     FROM myview 
     GROUP BY 
       id 
     ) md 
JOIN m.* 
ON  m.id = md.id 
     AND m.date = md.mindate 
5

¿Qué tal un pedido de GROUP_CONCAT?

SELECT value1, GROUP_CONCAT(value1 ORDER BY date DESC) 
FROM table1 
GROUP BY value1; 

Esa es la sintaxis que necesita suponer.