MySQL GROUP_CONCAT vs. COALESCE con respecto a los valores NULL
Acabo de notar que en el servidor la columnatable3.note
los valores sonNULL
y en mi máquina local son cadenas vacías. Después de este descubrimiento vergonzoso hice algunas pruebas y todo funciona de la misma manera en ambas plataformas.
Y esto es lo que producen si tengo dos celdas y la segunda contiene un valor real (la primera esNULL
):
//1st
GROUP_CONCAT(COALESCE(`table3`.`note`, '') SEPARATOR ';') AS `table3_note`
//var_dump(): array(2) { [0]=> string(0) "" [1]=> string(4) "Test" }
//2nd
GROUP_CONCAT(`table3`.`note`) SEPARATOR ';') AS `table3_note`
//var_dump(): array(1) { [0]=> string(4) "Test" }
Así que la primera consulta (COALESCE
) recuperaNULL
s como cuerdas vacías y las segundas tiras todasNULL
valores del conjunto de resultados. (Esto es inaceptable porque tengo muchas matrices y es necesario sincronizarlas).
El problema original se resuelve por culpa de mi error. Todavía me gustaría saber por quéGROUP_CONCAT
ignoraNULL
s incluso si está marcada.
Aquí está la consulta que funciona correctamente (no elimina laNULL
s):
SELECT `table1`.*
GROUP_CONCAT(COALESCE(`table3`.`id`, '') SEPARATOR ';') AS `t3_id`,
GROUP_CONCAT(COALESCE(`table3`.`note`, '') SEPARATOR ';') AS `t3_note`,
FROM `table1`
LEFT JOIN `table3` ON `table3`.`id` = `table1`.`id`
GROUP BY `table1`.`id`
Entonces, ¿por qué éste ignora?NULL
s? (Más opciones de consulta que ignoranNULL
Los valores están en la sección de preguntas original.)
SELECT `table1`.*
GROUP_CONCAT(`table3`.`id` SEPARATOR ';') AS `t3_id`,
GROUP_CONCAT(`table3`.`note` SEPARATOR ';') AS `t3_note`,
FROM `table1`
LEFT JOIN `table3` ON `table3`.`id` = `table1`.`id`
GROUP BY `table1`.`id`
Pregunta original (no importante, mi mal ...)Una parte de mi consulta que usa tres tablas (relación 1: n, estoy mapeando varias filas detable2
ytable3
a una solatable1
fila). Dos alternativas para obtener un solo valor de celda:
//1st
GROUP_CONCAT(COALESCE(`table3`.`note`, '') SEPARATOR ';') AS `table3_note`
//2nd
GROUP_CONCAT(`table3`.`note`) SEPARATOR ';') AS `table3_note`
Ambos funcionan bien en la máquina local, pero solo el primero en el servidor. En mi máquina local obtengo una cantidad correcta de valores de matriz vacíos cuando uso la primera o la segunda opción (usandovar_dump()
). En el servidor, la segunda opción devuelve solo una matriz vacía si no hay valores en ningunatable3_note
(Hay muchostable3_id
s y otros campos no mostrados en la consulta).
Entonces la pregunta es ¿por qué? Ambas funciones pretenden volverNULL
Si no hay valores no nulos según el manual.
¿Es relevante la siguiente información o me falta algo en el manual?
Máquina local: MySQL Client API versión 5.1.44Servidor: MySQL Client API versión 5.0.51a¿Es la respuesta tan simple que el servidor maneja elCOALESCE
Funciona como mi máquina local, pero laGROUP_CONCAT
¿La función se maneja de manera diferente debido a que las versiones de la API del cliente MySQL no coinciden?
Ahora tengo una solución operativa, por lo que no es una pregunta real en el sentido de que necesito arreglar esto. Me gustaría saber por qué esto es así. ¿Y hay alguna trampa en el uso deCOALESCE
como estoy usando? ¿Existe el peligro de que las matrices no estén sincronizadas correctamente al imprimirlas con unfor
¿lazo? (Al menos una prueba rápida no reveló ningún problema.)
Notas finales. Intenté usar estos y algunos otros métodos (IFNULL
, IS NULL
etc.) como sugerido por ejemplo en estas preguntas:
Pero el resultado fue el mismo: funciona en una máquina local pero no en el servidor. Consultas a continuación:
//another option for the query
IF(SUM(`table3`.`note` IS NULL) = 0, GROUP_CONCAT(`table3`.`note` SEPARATOR ';'), NULL) AS `table3_note`
//and another one...
ISNULL(GROUP_CONCAT(`table3`.`note` SEPARATOR ';'), '') AS `table3_note`
A menos que se indique lo contrario, las funciones de grupo ignoran los valores NULL.
Esto significaCOALESCE
no ignoraNULL
valores comoGROUP_CONCAT
hace, incluso si se comprueba? Esto todavía no explica los diferentes comportamientos del servidor y la máquina local. O lo hace?