2008-10-13 2 views
41

Что такое быстрый SQL для получения дубликатов в наборах данных с сотнями тысяч записей. Обычно я использую что-то вроде:Самый быстрый сценарий «Получить дубликаты» SQL

SELECT afield1, afield2 FROM afile a 
WHERE 1 < (SELECT count(afield1) FROM afile b WHERE a.afield1 = b.afield1); 

Но это довольно медленно.

ответ

74

Это более прямой путь:

select afield1,count(afield1) from atable 
group by afield1 having count(afield1) > 1 
15

Вы можете попробовать:

select afield1, afield2 from afile a 
where afield1 in 
(select afield1 
    from afile 
    group by afield1 
    having count(*) > 1 
); 
+2

Это действительно мой предпочтительный способ, потому что вы можете вернуть все столбцы таблицы. – leek 2008-10-13 12:15:26

+0

Как ни странно, 2 человека проголосовали за этот ответ, не комментируя почему. Я полагаю, это означает, что с ним что-то не так? – 2008-10-14 15:28:32

+0

Я бы предположил, что он медленнее – 2008-10-14 21:03:29

5

Аналогичный вопрос был задан на прошлой неделе. Там есть хорошие ответы.

SQL to find duplicate entries (within a group)

В этом вопросе, ОП был заинтересован во всех столбцов (полей) в таблицу (файл), но строки принадлежали в той же группе, если они имели один и тот же значение ключа (afield1).

Есть три вида ответов:

подзапросы в предложении где, как и некоторые другие ответы здесь.

внутреннее соединение между столом и группами рассматривать как таблицу (мой ответ)

и аналитических запросов (что-нибудь новое для меня).

5

Кстати, если кто-то хочет, чтобы удалить дубликаты, я использовал это:

delete from MyTable where MyTableID in (
    select max(MyTableID) 
    from MyTable 
    group by Thing1, Thing2, Thing3 
    having count(*) > 1 
) 
3

Это должно быть достаточно быстро (даже быстрее, если dupeFields индексируются).

SELECT DISTINCT a.id, a.dupeField1, a.dupeField2 
FROM TableX a 
JOIN TableX b 
ON a.dupeField1 = b.dupeField2 
AND a.dupeField2 = b.dupeField2 
AND a.id != b.id 

Я думаю, единственный недостаток этого запроса является то, что, потому что вы не делаете COUNT(*) вы не можете проверить на количество раз он дублируется, только то, что он выглядит более чем один раз.

Смежные вопросы