Как удалить все повторяющиеся записи в таблице MySQL без временных таблиц
Я видел несколько вариантов этого, но ничто не сравнимо с тем, что я пытаюсь выполнить.
У меня есть таблица TableA, в которой содержатся ответы, заданные пользователями для настраиваемых вопросников. Столбцы: member_id, quiz_num, question_num, answer_num.
Как-то несколько членов получили свои ответы дважды. Поэтому мне нужно удалить дублированные записи, но убедитесь, что одна строка оставлена позади. Нет "первичного" столбца, поэтому могут быть две или три строки с одинаковыми данными.
Есть ли запрос для удаления всех дубликатов?
Ответы
Ответ 1
Добавьте Уникальный индекс в таблицу:
ALTER IGNORE TABLE `TableA`
ADD UNIQUE INDEX (`member_id`, `quiz_num`, `question_num`, `answer_num`);
Другой способ сделать это:
Добавьте первичный ключ в свою таблицу, тогда вы можете легко удалить дубликаты из своей таблицы, используя следующий запрос:
DELETE FROM member
WHERE id IN (SELECT *
FROM (SELECT id FROM member
GROUP BY member_id, quiz_num, question_num, answer_num HAVING (COUNT(*) > 1)
) AS A
);
Ответ 2
Вместо drop table TableA
вы можете удалить все регистры (delete from TableA;
), а затем заполнить исходную таблицу регистрами, исходящими из TableA_Verify (insert into TAbleA select * from TAbleA_Verify
). Таким образом, вы не потеряете все ссылки на исходную таблицу (индексы,...)
CREATE TABLE TableA_Verify AS SELECT DISTINCT * FROM TableA;
delete from TableA;
INSERT INTO TableA SELECT * FROM TAbleA_Verify;
DROP TABLE TableA_Verify;
Ответ 3
Это не использует таблицы TEMP, а вместо этого - реальные таблицы. Если проблема связана только с временными таблицами, а не с таблицей создания или отбрасыванием таблиц, это будет работать:
SELECT DISTINCT * INTO TableA_Verify FROM TableA;
DROP TABLE TableA;
RENAME TABLE TableA_Verify TO TableA;
Ответ 4
Благодаря jveirasv для ответа выше.
Если вам нужно удалить дубликаты определенных наборов столбцов, вы можете использовать это (если у вас есть временная метка в таблице, которая может меняться, например)
CREATE TABLE TableA_Verify AS SELECT * FROM TableA WHERE 1 GROUP BY [COLUMN TO remove duplicates BY];
DELETE FROM TableA;
INSERT INTO TableA SELECT * FROM TAbleA_Verify;
DROP TABLE TableA_Verify;
Ответ 5
Добавьте уникальный индекс в таблицу:
ALTER IGNORE TABLE TableA
ADD UNIQUE INDEX (member_id, quiz_num, question_num, answer_num);
работает очень хорошо
Ответ 6
Если вы не используете какой-либо первичный ключ, выполните следующие запросы за один раз. Заменяя значения:
# table_name - Your Table Name
# column_name_of_duplicates - Name of column where duplicate entries are found
create table table_name_temp like table_name;
insert into table_name_temp select distinct(column_name_of_duplicates),value,type from table_name group by column_name_of_duplicates;
delete from table_name;
insert into table_name select * from table_name_temp;
drop table table_name_temp
- создать временную таблицу и сохранить отдельные (не дублируемые) значения
- сделать пустую исходную таблицу
- Вставить значения в исходную таблицу из таблицы temp
- удалить временную таблицу
Всегда рекомендуется делать резервную копию базы данных, прежде чем играть с ней.
Ответ 7
Как отмечено в комментариях, запрос в ответе Saharsh Shah должен выполняться несколько раз, если элементы дублируются более одного раза.
Здесь решение, которое не удаляет какие-либо данные, и сохраняет данные в исходной таблице все время, позволяя удалять дубликаты, сохраняя таблицу "live":
alter table tableA add column duplicate tinyint(1) not null default '0';
update tableA set
duplicate=if(@member_id=member_id
and @quiz_num=quiz_num
and @question_num=question_num
and @answer_num=answer_num,1,0),
member_id=(@member_id:=member_id),
quiz_num=(@quiz_num:=quiz_num),
question_num=(@question_num:=question_num),
answer_num=(@answer_num:=answer_num)
order by member_id, quiz_num, question_num, answer_num;
delete from tableA where duplicate=1;
alter table tableA drop column duplicate;
В основном это проверяет, совпадает ли текущая строка с последней строкой, и если это так, отмечает ее как дубликат (инструкция заказа гарантирует, что дубликаты будут отображаться рядом друг с другом). Затем вы удаляете дубликаты записей. Я удаляю столбец duplicate
в конце, чтобы вернуть его в исходное состояние.
Похоже, что alter table ignore
также скоро исчезнет: http://dev.mysql.com/worklog/task/?id=7395
Ответ 8
Альтернативным способом было бы создать новую временную таблицу с той же структурой.
CREATE TABLE temp_table AS SELECT * FROM original_table LIMIT 0
Затем создайте первичный ключ в таблице.
ALTER TABLE temp_table ADD PRIMARY KEY (primary-key-field)
Наконец, скопируйте все записи из исходной таблицы, игнорируя повторяющиеся записи.
INSERT IGNORE INTO temp_table AS SELECT * FROM original_table
Теперь вы можете удалить исходную таблицу и переименовать новую таблицу.
DROP TABLE original_table
RENAME TABLE temp_table TO original_table