sql >> Base de Datos >  >> RDS >> Mysql

MySQL no usa índices (usando filesort) cuando usa ORDER BY

No puede usar un índice en este caso, ya que usa un RANGE condición de filtrado.

Si usara algo como:

SELECT  *
FROM    values_table this_
WHERE   this_.value1 = @value
ORDER BY
        value2
LIMIT 10

, luego crea un índice compuesto en (VALUE1, VALUE2) se usaría tanto para filtrar como para ordenar.

Pero usa una condición a distancia, es por eso que deberá realizar el pedido de todos modos.

Su índice compuesto se verá así:

value1 value2
-----  ------
1      10
1      20
1      30
1      40
1      50
1      60
2      10
2      20
2      30
3      10
3      20
3      30
3      40

y si selecciona 1 y 2 en value1 , aún no obtiene un conjunto ordenado completo de value2 .

Si su índice en value2 no es muy selectivo (es decir, no hay muchos DISTINCT value2 en la tabla), podría intentar:

CREATE INDEX ix_table_value2_value1 ON mytable (value2, value1)

/* Note the order, it's important */    

SELECT  *
FROM    (
        SELECT  DISTINCT value2
        FROM    mytable
        ORDER BY
                value2
        ) q,
        mytable m
WHERE   m.value2 >= q.value2
        AND m.value2 <= q.value2
        AND m.value1 BETWEEN 13123123 AND 123123123

Esto se llama SKIP SCAN método de acceso. MySQL no lo admite directamente, pero se puede emular así.

El RANGE en este caso se utilizará el acceso, pero probablemente no obtendrá ningún beneficio de rendimiento a menos que DISTINCT value2 comprende menos del 1% de filas.

Tenga en cuenta el uso de:

m.value2 >= q.value2
AND m.value2 <= q.value2

en lugar de

m.value2 = q.value2

Esto hace que MySQL realizar RANGE comprobando cada ciclo.