sql >> Databáze >  >> RDS >> Mysql

MySQL nepoužívá indexy (Using filesort) při použití ORDER BY

V tomto případě nemůžete použít index, protože používáte RANGE podmínky filtrování.

Pokud byste použili něco jako:

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

a poté vytvořte složený index na (VALUE1, VALUE2) by bylo použito jak pro filtrování, tak pro objednávání.

Vy ale používáte podmínku rozsahu, proto budete stejně muset provést řazení.

Váš složený index bude vypadat takto:

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

a pokud vyberete 1 a 2 v value1 , stále nedostanete celou seřazenou sadu value2 .

Pokud je váš index na value2 není příliš selektivní (tj. není mnoho DISTINCT value2 v tabulce), můžete zkusit:

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

Toto se nazývá SKIP SCAN přístupová metoda. MySQL přímo nepodporuje, ale lze jej takto emulovat.

RANGE v tomto případě bude použit přístup, ale pravděpodobně nezískáte žádnou výkonnostní výhodu, pokud DISTINCT value2 obsahovat méně než asi 1% řádků.

Poznámka použití:

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

místo

m.value2 = q.value2

To dělá MySQL provést RANGE kontrola každé smyčky.



  1. Pochopení aliasů Oracle – proč není alias v dotazu rozpoznán, pokud není zabalen do druhého dotazu?

  2. SQL Server 2016:Vytvořte uloženou proceduru

  3. Pochopení ztráty událostí s prodlouženými událostmi

  4. Snažím se vytvořit statickou databázovou třídu, ke které mám přístup z jakékoli funkce mimo třídu