Я работаю над сценарием PostgreSQL 8.1 SQL, который должен удалить большое количество строк из таблицы.
Допустим, таблица, из которой мне нужно удалить, это Employees (~ 260K строк).
У него есть первичный ключ с именем id.
Строки, которые мне нужно удалить из этой таблицы, хранятся в отдельной временной таблице EmployeesToDelete (~ 10K записей) со ссылкой на внешний ключ Employees.id, называемой employee_id.
Есть ли эффективный способ сделать это?
Сначала я подумал о следующем:
DELETE
FROM Employees
WHERE id IN
(
SELECT employee_id
FROM EmployeesToDelete
)
Но я слышал, что использование предложения IN и подзапросов может быть неэффективным, особенно для больших таблиц.
Я посмотрел документацию по PostgreSQL 8.1, и там есть упоминание о
УДАЛИТЬ ОТ ... ИСПОЛЬЗОВАНИЯ, но у него нет примеров, поэтому я не уверен, как его использовать.
Мне интересно, работает ли следующее и более ли оно эффективно?
DELETE
FROM Employees
USING Employees e
INNER JOIN
EmployeesToDelete ed
ON e.id = ed.employee_id
Ваши комментарии очень ценятся.
Edit:
Я запустил EXPLAIN ANALYZE, и странно то, что первый DELETE работал довольно быстро (в течение нескольких секунд), в то время как второй DELETE занял так много времени (более 20 минут), и я в конце концов отменил его.
Добавление индекса во временную таблицу значительно улучшило производительность.
Вот план запроса первого УДАЛИТЬ для всех, кто интересуется:
Hash Join (cost=184.64..7854.69 rows=256482 width=6) (actual time=54.089..660.788 rows=27295 loops=1)
Hash Cond: ("outer".id = "inner".employee_id)
-> Seq Scan on Employees (cost=0.00..3822.82 rows=256482 width=10) (actual time=15.218..351.978 rows=256482 loops=1)
-> Hash (cost=184.14..184.14 rows=200 width=4) (actual time=38.807..38.807 rows=10731 loops=1)
-> HashAggregate (cost=182.14..184.14 rows=200 width=4) (actual time=19.801..28.773 rows=10731 loops=1)
-> Seq Scan on EmployeesToDelete (cost=0.00..155.31 rows=10731 width=4) (actual time=0.005..9.062 rows=10731 loops=1)
Total runtime: 935.316 ms
(7 rows)
На этом этапе я буду придерживаться первого УДАЛЕНИЯ, если не найду лучшего способа его написания.