Wpływ indeksu na instrukcje aktualizacji, gdy kolumna aktualizacji nie znajduje się w indeksie

16

I ciągle widzę ludzi powiedzieć, że indeksy spowolnić update, deletea insert. Jest to używane jako instrukcja zbiorcza, tak jakby była absolutem.

Podczas dostrajania mojej bazy danych w celu poprawy wydajności ciągle napotykam na tę sytuację, która wydaje mi się logicznie sprzeczna z tą regułą i nigdzie nie mogę znaleźć nikogo, kto by powiedział lub wyjaśnił w jakikolwiek inny sposób.

W SQL Server i uważam / zakładam, że większość innych DBMS, twoje indeksy są tworzone na podstawie określonych kolumn, które określisz. Wstawianie i usuwanie zawsze wpływa na cały wiersz, więc nie ma mowy, aby nie wpływały na indeks, ale aktualizacje wydają się nieco bardziej unikalne, mogą w szczególności wpływać tylko na niektóre kolumny.

Jeśli mam kolumny, które nie są uwzględnione w żadnym indeksie i aktualizuję je, czy są one spowolnione tylko dlatego, że mam indeks w innych kolumnach w tej tabeli?

Na przykład powiedzmy w mojej Usertabeli, że mam jeden lub dwa indeksy, klucz podstawowy, który jest kolumną Identity / Auto Increment, i ewentualnie inny w kolumnie z kluczem obcym.
Jeśli zaktualizuję kolumnę bez indeksu bezpośrednio na niej, na przykład podając numer telefonu lub adres, czy ta aktualizacja zostanie spowolniona, ponieważ mam indeksy w tej tabeli w innych kolumnach w obu sytuacjach? Aktualizowane przeze mnie kolumny nie znajdują się w indeksach, więc logicznie indeksy nie powinny być aktualizowane, prawda? Jeśli cokolwiek, sądzę, że zostaną przyspieszone, jeśli użyję indeksów w klauzuli WHERE.

Ryan
źródło
so there is no way they will not affect the indexz wyjątkiem przefiltrowanych indeksów ...
usr
Myślę, że nieobjęty, nieklastrowany indeks zawiera wskaźniki do rekordów (zwykle w węzłach liści indeksów klastrowych). Wydaje mi się, że jedną z sytuacji powodujących spowolnienie podczas aktualizacji (nieuwzględnionego atrybutu) może być sytuacja, w której aktualizacja spowodowała przesunięcie rekordu w indeksie klastrowym. Nadal nie jestem pewien, czy ruch spowodowałby zmianę wskaźnika, LUB czy wskaźnik jest po prostu wartością KLUCZOWĄ w indeksie klastrowym, w którym to przypadku możliwa aktualizacja lokalizacji nie miałaby znaczenia, ponieważ system po prostu przeprowadziłby wyszukiwanie klucza aby uzyskać wartość rekordu.
Jmoney38

Odpowiedzi:

6

Masz rację, że aktualizacja nieindeksowanej kolumny nie spowoduje zmian w indeksach. W prostym przypadku ogólny wpływ na stół również nie byłby.

Jeśli zapytanie może wykorzystywać Indeks do wyszukiwania danych, może to przyspieszyć wyszukiwanie, ale dokładne zachowanie (w zależności od marki SQL) może różnić się od SQL innych marek SQL. (Używam głównie Microsoft SQL Server.)

Oczywiście aktualizacja kolumny ze znacznie większą ilością danych może spowodować pewne przeniesienie wierszy na różne strony itp.

RLF
źródło
1
SQL Server jest wspomniany w OP, dodałem tag, więc myślę, że możesz założyć SQL Server
Tom V - Team Monica
10

W przypadku stosunkowo szybkiego nowoczesnego systemu dodanie jednego indeksu do tabeli OLTP będzie prawdopodobnie praktycznie niewykrywalne z punktu widzenia wydajności dla zdecydowanej większości systemów . To powiedziawszy, nie powinieneś tworzyć niepotrzebnych indeksów i prawdopodobnie nie powinieneś tworzyć indeksów jednokolumnowych dla każdej kolumny w tabeli.

Masz rację, zakładając, że w przypadku wielu zapytań obecność przydatnych indeksów spowoduje bardzo zauważalną poprawę prędkości.

Chociaż wydaje się, że Twoje pytanie dotyczy wydajności, istnieje kilka innych potencjalnych problemów związanych z dodawaniem indeksów, w tym między innymi:

  1. Czas wymagany do utworzenia indeksu może spowodować zablokowanie podczas dodawania indeksu do tabeli. Zamek jest bardzo krótkotrwały i najprawdopodobniej nie spowoduje dużego problemu.

  2. Zmiany indeksu powodują unieważnienie planów wykonania dla wszystkich planów, które odwołują się do podstawowej tabeli. Po ponownej kompilacji tych planów wykonania wydajność może się negatywnie zmienić w przypadku niektórych zapytań.

  3. Modyfikacje indeksu mogą powodować zwracanie przez zapytania błędów, w przypadku których żadne wcześniej nie zostało zwrócone. Weźmy na przykład filtrowany indeks, który został użyty do zwrócenia dat zawartych w polu varchar; jeśli filtr wyeliminował wszystkie wiersze, które nie były datami, a filtr ten został następnie zmieniony, zapytania oparte na tym indeksie mogą teraz nie powieść się podczas próby konwersji danych innych niż data.

  4. Nowy indeks może powodować zmianę kolejności wykonywania, czego skutkiem mogą być zakleszczenia, o ile nie wystąpiły wcześniej.

Max Vernon
źródło
„Ścieżka do kodu wymagana do aktualizacji, gdy nie ma to wpływu na indeks, nadal wymaga oceny”, to nie jest prawda. Faza kompilacji / optymalizacji będzie bardzo dobrze wiedziała, jakie indeksy należy zaktualizować, jeśli takie istnieją, i odpowiednio utworzy plan. Instrukcja UPDATE, która nie modyfikuje (deklaruje na liście SET) kolumn w indeksie (w tym INCLUDE i kolumn kluczy klastrowych) nie będzie musiała aktualizować tego indeksu, a faza wykonania nawet go nie dotknie. DELETE i INSERT oczywiście dotykają wszystkich kolumn (logicznie) i muszą zaktualizować wszystkie indeksy.
Remus Rusanu
@RemusRusanu, ale czy nie trzeba będzie oceniać, czy indeks można wykorzystać do zlokalizowania wierszy wymagających aktualizacji?
Tom V - Team Monica
@RemusRusanu - Przypuszczam, że kiedy QO opracuje plan, nie będzie już potrzebny procesor; jednak aby skompilować plan, z pewnością musi to zrobić. Jeśli plany są często kompilowane, może to mieć bardzo niewielką różnicę.
Max Vernon
@TomV korzystanie z indeksu w celu zlokalizowania wierszy kandydujących do usunięcia / aktualizacji to zupełnie inny temat. W takim przypadku korzyści z lokalizacji wierszy za pomocą indeksu powinny pokonać wszelkie problemy z utrzymaniem indeksu.
Remus Rusanu
@ MaxVernon Argumentowałbym, że nie ma prawidłowego scenariusza częstych ponownych kompilacji DML (UPDATE). Kupuję niektóre przypadki poprawnych (nieuniknionych?) Ponownych kompilacji w przypadku zapytań ad hoc. Ale DML? Jaka aplikacja może tworzyć ad-hoc unikalne instrukcje UPDATE? Częste rekompilacje z DML wołają głośno „Sparametryzuj mnie”.
Remus Rusanu
-2

Jeśli operacja aktualizacji jest skierowana na nieindeksowaną kolumnę o stałym rozmiarze (np. Liczbę całkowitą), ogólnie rzecz biorąc nie powinna być wolna, ale w porównaniu z instrukcją select, aktualizacja musi zostać ostatecznie zapisana również na wolnym dysku.

Sorin
źródło