¿Por qué las siguientes consultas copian los datos de la tabla?
-
10-10-2019 - |
Pregunta
SELECT COUNT(*) AS cnt
FROM products
WHERE ExternalProductId IS NOT NULL
GROUP BY SourceId, ExternalProductId
HAVING cnt > 1
Hay un índice en (ExternalProductid, SourceId, Otherfield). Una explicación muestra que se utiliza el índice. Esto se imprime en la columna "extra" de explicación:
Using where; Using index; Using temporary; Using filesort
Cuando ejecuto la consulta que veo a través de Show ProcessList:
Copying to tmp table on disk
¿Puedo modificar esta consulta para que funcione en el índice? Tampoco me importa si los resultados que obtengo son ligeramente inexactos debido a que otros procesos trabajan simultáneamente en esta tabla: ¿puedo cambiar el nivel de aislamiento para aumentar el rendimiento de la consulta?
Solución
Si invierte las columnas en su GROUP BY
Para corresponder con el orden de los dos primeros campos de su índice de compuesto, utilizará su índice compuesto de manera mucho más efectiva.
SELECT COUNT(*) AS cnt
FROM products
WHERE ExternalProductId IS NOT NULL
GROUP BY ExternalProductId, SourceId
HAVING cnt > 1
La ejecución de su consulta debe convertirse en 'Using where; Using index'
, y deshacerse de la tabla temporal y filsort causada por la otra GROUP BY
.
Todavía obtendrá los mismos resultados, pero estará en un orden ligeramente diferente.
Otros consejos
Un par de cosas para probar:
MySQL ordenará automáticamente con un grupo por. Si no le importa el orden de clasificación, agregue una cláusula 'Orden por NULL'. Eso eliminará el FileSort y posiblemente la tabla TEMP.
Elimine el recuento (*) y use el nombre de una columna en el índice en lugar del comodín.
También. ¿Cuál es tu índice? ¿Puedes mostrarnos la declaración de creación de tabla completa?