Nie jest łatwo odpowiedzieć na to pytanie. Powinieneś wiedzieć jedną ważną rzecz:MySQL traktuje IN (<static values list>) i IN (<subquery>) jako różne zapytania
. Pierwszy jest równy porównaniu zakresów (np. .. OR = .. OR = ) podczas gdy sekunda jest równa = ANY () - i to nie to samo. Krótko mówiąc:używając IN z podzapytanie spowoduje zapytanie z ANY() a MySQL nie użyje do tego indeksu, nawet jeśli podzapytanie jest niezależne i zwraca statyczną listę wartości . Smutne ale prawdziwe. MySQL nie może tego przewidzieć, więc indeks nie zostanie użyty, nawet jeśli jest to oczywiste. Jeśli użyjesz JOIN (tj. przepisz swój IN (<subquery>) ) - wtedy MySQL użyje indeksu do JOIN warunek, jeśli to możliwe.
Teraz drugi przypadek może dotyczyć JOIN i IN podczas korzystania z partycji. Jeśli użyjesz JOIN - to niestety - ale MySQL również nie jest w stanie przewidzieć partycji dla JOIN w zwykłym przypadku - i użyje do tego całego zestawu partycji. Zastępowanie JOIN na IN (<static list>) zmieni EXPLAIN PARTITION obrazek:MySQL użyje tylko tych partycji, które są potrzebne do wybrania wartości z zakresu określonego w IN klauzula. Ale znowu to nie zadziała z IN (<subquery>) .
Podsumowując - to smutne, gdy mówimy o tym, jak MySQL obsługuje IN podzapytania - i w powszechnym przypadku nie można ich zastąpić przez JOIN bezpiecznie (chodzi o partycjonowanie przypadku). Dlatego powszechnym rozwiązaniem będzie:oddziel podzapytanie od głównego zapytania na poziomie aplikacji . Jeśli mówimy o niezależnym podzapytaniu, zwracającym listę wartości statycznych, to jest to najlepsza sugestia - wtedy możesz podstawić tę listę wartości jako IN(<static list>) i zyskaj korzyści:MySQL użyje do tego indeksu, a jeśli mówimy o partycjach, zostaną użyte tylko faktycznie potrzebne z nich.