Zde je to, co jsem udělal, a zkrátil celkovou dobu provádění o faktor 10.
Co jsem si uvědomil z plánu provádění mého původního dotazu, bylo to, že používal řazení souborů pro třídění všech výsledků a ignorování indexů. To je trochu plýtvání.
Moje testovací databáze:5 M záznamů, velikost 20 GB. struktura tabulky stejná jako v otázce
Namísto získání blobCol přímo v prvním dotazu nejprve získám hodnotu 'name' pro začátek každé stránky. Spouštějte tento dotaz po neomezenou dobu, dokud nevrátí 0 výsledků. Pokaždé přidejte výsledek do seznamu
SELECT name
FROM my_table
where id = <anyId> // I use the id column for partitioning so I need this here
order by name
limit <pageSize * pageNumber>, 1
Číslo sinusové stránky není dříve známé, začněte s hodnotou 0 a zvyšujte se, dokud dotaz nevrátí hodnotu null. Můžete také provést select count(*), ale to samo o sobě může trvat dlouho a nepomůže nic optimalizovat. Spuštění každého dotazu trvalo přibližně 2 sekundy, jakmile číslo stránky přesáhlo ~60.
Pro mě byla velikost stránky 5000, takže jsem dostal seznam řetězců 'name' na pozici 0, 5001, 10001, 15001 a tak dále. Ukázalo se, že počet stránek je 1000 a uložení seznamu 1000 výsledků do paměti není drahé.
Nyní projděte seznam a spusťte tento dotaz
SELECT blobCol
FROM my_table
where name >= <pageHeader>
and name < <nextPageHeader>
and city="<any string>"
and id= 1
Toto se spustí Nkrát, kde N =velikost dříve získaného seznamu. Protože 'name' je sloupec primárního klíče a 'city' je také indexováno, EXPLAIN ukazuje, že tento výpočet se provádí v paměti pomocí indexu.
Nyní trvá spuštění každého dotazu 1 sekundu namísto původních 30–40. Kombinací doby předběžného zpracování 2 sekundy na stránku je tedy celkový čas na stránku 3–4 sekundy namísto 30–40.
Pokud má někdo lepší řešení nebo pokud je s tímto něco do očí bijícího špatně, dejte mi prosím vědět