Polecenie Delete w SQL jest bardzo wolne

Mam takie wypowiedzi, które nie działają:

DELETE FROM [table] WHERE [COL] IN ( '1', '2', '6', '12', '24', '7', '3', '5')

Próbowałem robić takie na raz:

DELETE FROM [table] WHERE [COL] IN ( '1' )
/ Align = "left" /

Tabela zawiera 260 000 wierszy i składa się z czterech kolumn.

Czy ktoś ma jakieś pomysły, dlaczego tak wolno i jak to przyspieszyć? Mam nie unikalny, Nie klastrowy indeks na [COL], który robię gdzie na. Używam SQL Server 2008 R2

Update: nie mam wyzwalaczy na stolik.

Author: Kyle, 2012-06-05

11 answers

Rzeczy, które mogą powodować powolne Usuwanie:

  • Usuwanie wielu rekordów
  • wiele indeksów
  • Brak indeksów w klawiszach obcych w tabelach potomnych. (dziękuję @ CesarAlvaradoDiaz za wzmiankę o tym w komentarzach)
  • deadlocks and blocking
  • wyzwalacze
  • cascade delete (te dziesięć rekordów nadrzędnych, które usuwasz, może oznaczać miliony rekordów dzieci są usuwane)
  • dziennik transakcji]} Wiele kluczy obcych do check

Więc możesz wybrać, aby dowiedzieć się, co blokuje i naprawić to lub uruchomić usuwanie w godzinach poza godzinami, gdy nie będą one zakłócać normalnego obciążenia produkcyjnego. Możesz uruchomić usuwanie w partiach (przydatne, jeśli masz wyzwalacze, kaskadowe usuwanie lub dużą liczbę rekordów). Możesz upuścić i odtworzyć indeksy(najlepiej, jeśli możesz to zrobić również w godzinach poza godzinami).

 60
Author: HLGEM,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-02 15:39:47
  1. Wyłącz ograniczenie

    ALTER TABLE [TableName] NOCHECK CONSTRAINT ALL;

  2. Wyłącz Indeks

    ALTER INDEX ALL ON [TableName] DISABLE;

  3. Rebuild Index

    ALTER INDEX ALL ON [TableName] REBUILD;

  4. Enable CONSTRAINT

    ALTER TABLE [TableName] CHECK CONSTRAINT ALL;

  5. Delete again

 39
Author: Shahab J,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-07-10 03:49:57

Usuwanie wielu wierszy może być bardzo powolne. Spróbuj usunąć kilka na raz, jak:

delete top (10) YourTable where col in ('1','2','3','4')
while @@rowcount > 0
    begin
    delete top (10) YourTable where col in ('1','2','3','4')
    end
 16
Author: Andomar,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-05 16:48:31

Działania Zapobiegawcze

Sprawdź za pomocą SQL Profiler przyczynę tego problemu. Może dojść do Triggers spowodowania opóźnienia w wykonaniu. To może być cokolwiek. Nie zapomnij wybrać Database Name i Object Name podczas uruchamiania Trace, aby wykluczyć skanowanie niepotrzebnych zapytań...

Filtrowanie Nazw Baz Danych

Filtrowanie Tabeli/Procedury Składowanej/Nazwy Wyzwalacza

Działania Naprawcze

Jak powiedziałeś twoja tabela zawiera 260,000 rekordów...i IN Predicate zawiera sześć wartości. Teraz każdy rekord jest przeszukiwany 260 000 razy dla każdej wartości w IN Predicate. Zamiast tego powinno to być wewnętrzne połączenie jak poniżej...

Delete K From YourTable1 K
Inner Join YourTable2 T on T.id = K.id

Wstaw wartości IN Predicate do Temporary Table lub Local Variable

 4
Author: ,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-05 17:28:11

Jeśli tabela, z której usuwasz, ma wyzwalacze przed / po usunięciu, coś tam może powodować opóźnienie.

DODATKOWO, jeśli masz klucze obce odwołujące się do tej tabeli, mogą wystąpić dodatkowe aktualizacje lub usunięcia.

 2
Author: sybkar,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-05 16:45:58

Jest możliwe, że inne tabele mają ograniczenia FK do Twojej [tabeli]. Tak więc DB musi sprawdzić te tabele, aby zachować integralność odniesienia. Nawet jeśli masz wszystkie potrzebne indeksy odpowiadające tym FK, sprawdź ich ilość.

Miałem sytuację, gdy NHibernate nieprawidłowo utworzony powielał FKs na tych samych kolumnach, ale z różnymi nazwami (co jest dozwolone przez SQL Server). Drastycznie spowolniło to działanie polecenia DELETE.

 1
Author: flam3,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-12-07 09:06:41

Czy [COL] naprawdę jest polem znaków, które zawiera liczby, czy możesz pozbyć się pojedynczych cudzysłowów wokół wartości? @Alex ma rację, że IN jest wolniejsze niż=, więc jak dasz radę to będzie lepiej:

DELETE FROM [table] WHERE [COL] = '1'

Ale nadal lepiej jest używać liczb, a nie ciągów, aby znaleźć wiersze (sql lubi liczby):

 DELETE FROM [table] WHERE [COL] = 1

Może spróbuj:

 DELETE FROM [table] WHERE CAST([COL] AS INT) = 1

W obu przypadkach upewnij się, że masz indeks na kolumnie [COL], aby przyspieszyć skanowanie tabeli.

 0
Author: Russell Fox,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-05 17:59:04

Sprawdź plan wykonania tego polecenia delete. Sprawdź, czy używane jest wyszukiwanie indeksów. Co to jest typ danych col?

Jeśli używasz niewłaściwego typu danych, Zmień instrukcję update(np. z '1' na 1 lub N '1').

Jeśli używane jest skanowanie indeksu rozważ użycie podpowiedzi query hint ..

 0
Author: Jānis,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-06 08:26:53

Przeczytałem ten artykuł, który był bardzo pomocny w rozwiązywaniu wszelkich niedogodności

Https://support.microsoft.com/en-us/kb/224453

To jest przypadek waitresource Klucz: 16: 72057595075231744 (ab74b4daaf17)

-- First SQL Provider to find the SPID (Session ID)

-- Second Identify problem, check Status, Open_tran, Lastwaittype, waittype, and waittime
-- iMPORTANT Waitresource select * from sys.sysprocesses where spid = 57

select * from sys.databases where database_id=16

-- with Waitresource check this to obtain object id 
select * from sys.partitions where hobt_id=72057595075231744

select * from sys.objects where object_id=2105058535
 0
Author: Eduardo,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-10-22 20:27:40

Jeśli usuwasz wszystkie rekordy w tabeli, a nie kilka wybranych, może być znacznie szybciej po prostu upuścić i odtworzyć tabelę.

 0
Author: lastlink,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-03-20 21:13:46

Otwórz CMD i uruchom to polecenie

NET STOP MSSQLSERVER
NET START MSSQLSERVER

Spowoduje ponowne uruchomienie instancji SQL Server. spróbuj uruchomić ponownie po poleceniu delete

Mam to polecenie w skrypcie wsadowym i uruchamiam je od czasu do czasu, jeśli napotkam takie problemy. Normalny restart komputera nie będzie taki sam, więc ponowne uruchomienie instancji jest najskuteczniejszym sposobem, jeśli napotkasz pewne problemy z serwerem sql.

 -4
Author: Mhelboy,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-02-05 11:26:32