![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Удалить дубли в таблице [D7, IB6.x]
Vlad © (2003-09-25 10:26:00)
Доброго всем времени суток.
Есть таблица, в которой основные поля: ID (integer,уникальное), Код(integer), Дата(Date), Наименование(Varchar).
Помимо них есть еще штук 15 полей.
Нужно из таблицы удалить дублирующие записи, так, чтобы связка Код-Дата-Наименование стала уникальной.
Проблема в том что в таблице порядка 12 млн записей.
Кто нибудь подскажет наиболее быстрый алгоритм решения задачи, выполнение которого было бы <= 24 часа ?
Все перепробованные мной способы, по предварительным подсчетам, выполнялись быкак минимум трое суток.
Спасибо.
NAlexey (2003-09-26 15:54:00) [1]
Все это конечно интересно, но при создании индексов также необходимо учитывать насколько интенсивно происходит удаление-вставка в таблицу. А то может получиться что выборка летает, а при добавлении записи или каскадном удалениии сидим и ждем.
Vlad (2003-09-26 15:48:00) [2]
>DenK_vrtz © (26.09.03 15:13) [52]
Уточню.
Грамотный запрос + нужныеиндексы + грамотный оптимизатор = великая сила :)
DenK_vrtz (2003-09-26 15:13:00) [3]
Грамотный запрос + Индексы = сила!!! :-)
Был тут у меня отчет. 22 минуты выполнялся(типа, сделал попробовал). Создал три! индекса, одну вьюшку подумал-переписал.
Результат - 45 сек!
kaif (2003-09-26 13:58:00) [4]
Конечно, мне интересен и этот результат.
Хотя исходная задача уже решена блестяще (успеть менее, чем за сутки удалить дубликаты).
Я предлагал альтернативное решение только потому что не верил в скоростную приемлемость решения Johnmen...
Vlad (2003-09-26 13:47:00) [5]
>kaif © (26.09.03 13:44) [49]
Твой вариант с ХП я буду пробовать на выходных, посмотрим что он даст по скорости.
kaif (2003-09-26 13:44:00) [6]
Потрясающий результат!
Johnmen, мое почтение.
Зря, видно, я стараюсь обходиться самыми примитивными запросами.
Vlad (2003-09-26 12:25:00) [7]
>Johnmen © (26.09.03 12:08) [46]
Кстати, по поводу планов. Ведь я использую Yaffil, а там, в отличие от самого IB существенно оптимизирован алгоритм их построения. Так что наши с тобой результаты могут отличаться, если ты используешь IB
Vlad (2003-09-26 12:18:00) [8]
Ок. Дома ради интереса попробую. В понедельник тогда отпишу.
Хотя вобщем моя цель уже достигнута. Дубли удалены. Их, кстати, как я и подозревал оказалось почти 1 млн.
Johnmen (2003-09-26 12:08:00) [9]
>Vlad © (26.09.03 11:42)
Да, можно и так попробовать. Но у меня есть некоторые сомнения по поводу оптимизации запроса.
Вобщем, попробуй и так и со врем.табл., если будет время/желание.
Vlad (2003-09-26 11:42:00) [10]
А зачем при этом создавать временную таблицу ?
Почему нельзя чтобы ХП просто возвращала список ID, которые принадлежат дублирующим записям ?
Тогда: DELETE FROM Table WHERE ID IN (SELECT ID FROM Хранимая_процедура)
Johnmen (2003-09-26 11:33:00) [11]
>Vlad ©
Кстати, я тут подумал на предложениями kaif ©, и вот предлагаю попробовать такую схему (только если борьба за скорость):
1.CREATE TABLE Temp (ID INT)
2. Хр.процедура, общая схема :
DECLARE VARIABLE i1 INT
DECLARE VARIABLE v1, v2, v3, vo1, vo2, vo3 VARCHAR
vo1=""; vo2=""; vo3="";
FOR SELECT ID,f1,f2,f3 FROM Table INTO :i1,:v1,:v2,:v3
ORDER BY f1,f2,f3 DO BEGIN
IF ((v1=vo1) AND (v2=vo2) AND (v3=vo3)) THEN
INSERT INTO Temp VALUES(:i1);
vo1=v1; vo2=v2; vo3=v3;
END
3. Отрабатываем процедуру
4.DELETE FROM Table WHERE ID IN (SELECT ID FROM Temp)
5.DROP TABLE Temp
Очень интересует скорость ! :)
Johnmen (2003-09-26 11:10:00) [12]
>Vlad © (26.09.03 10:35)
Жаль... Придется самому пробовать, когда выдастся достаточно своб.времени...:)
Vlad (2003-09-26 10:35:00) [13]
>Johnmen © (26.09.03 10:32) [41]
К сож. YaP упорно молчит про планы :) Так уж он устроен.
Пишет только то, что использовался тот самый составной индекс.
Johnmen (2003-09-26 10:32:00) [14]
>Vlad ©
>DenK_vrtz ©
Мужики, не смущайте меня :) Мне неловко...
>Vlad ©
Если несложно, приведи планы выполнения запросов [2] и [12].
Мне почему-то представлялось, что [12] д.б. быстрее [2]...
Но на этот вопрос дадут ответ планы.
Vlad (2003-09-26 10:29:00) [15]
В любом случае, спасибо всем кто участвовал.
Конечно не ожидал я такого результата.
При проверке на 100 тыс. надо было видеть мое выражение лица!
Готовый к самому худшему, налил кофе, нарезал бутербродов, взял секундомер, приготовился ждать. И на тебе ! 2 секунды :)))
DenK_vrtz (2003-09-26 10:22:00) [16]
Vlad ©, мои поздравления!
Johnmen ©, мои восхищения! Это круто!
Vlad (2003-09-26 10:12:00) [17]
Тестировал при количестве записей - 100 тысяч.
Вобщем результаты были выше всяких похвал.
По совету Johnmen © добавил составной индекс.
Результат:
[2] - 2 сек.
[12] - 3 сек.
[27] - запрос повел себя немного странно. Загрузка ЦП - 99%, при этом обращения к жесткому диску были оч. редкими, судя по лампочке. Короче на 10-й минуте ожидания снял задачу. Чтоб убедиться проверил еще раз. Тоже самое.
А теперь, внимание, смертельный номер. Количество записей 12 МЛН.
Используется запрос [2].
Результат - 1 час 20 мин. !!!
Johnmen ©, ты - гений ! Как я сам не догадался про составной индекс ?! Без него все было на несколько порядков медленнее.
Johnmen (2003-09-26 10:02:00) [18]
Мне интересно !!!
DenK_vrtz (2003-09-26 09:59:00) [19]
Канэчно!!! :-) С нетерпением ждем(c)
Vlad (2003-09-26 09:56:00) [20]
DenK_vrtz ©, Johnmen ©, kaif © и все кто участвовал.
Вам еще интересны результаты моих лабораторных опытов, касательно обсуждаемой вчера темы ?