面试题:mysql删除重复记录,保留id最小的数据

时间:2024-05-23 21:54:32

前提说明:数据库采用的是mysql。 
数据库表格: 

面试题:mysql删除重复记录,保留id最小的数据

题目: 
删除name相同的行,并且保留的行是最小行。 
思路: 
1.找出除了编号不同,其他信息不全相同的编号。 
关键词:group by……having :分组查询,我对这个关键词的理解是:不同的行之间找出列相同的一项或者几项,几项都需要相同用逗号隔开。查询的几行值中如果还需要条件过滤,那么需要用having来过滤。 
sql语句如下: 
select id from t_test20191023 group by name 
2.从总表中删除信息不在第一步查询中得到的编号的数据 
delete from t_test20191023 where id not in (select id from t_test20191023 group by name order by id)

写到这里,sql语句看似写的完美,但是在mysql中运行时,会出现这个错误: 

面试题:mysql删除重复记录,保留id最小的数据

这个错误的原因是:更新这个表的同时又查询了这个表,查询这个表的同时又去更新这个表,可以理解为死锁,所以出现了这个问题。

解决方法: 
在第一步中查询最小的id时,不从主表中去查找,而是根据需要的字段从构建一个第三个表,从第三个表中去获取数据。 
select id from (select id from t_test20191023 group by name order by id) 

报错
[Err] 1248 - Every derived table must have its own alias

面试题:mysql删除重复记录,保留id最小的数据

必须给表起个别名

select id from (select id from t_test20191023 group by name order by id) b

面试题:mysql删除重复记录,保留id最小的数据

然后删除

面试题:mysql删除重复记录,保留id最小的数据

面试题:mysql删除重复记录,保留id最小的数据

这样也是可以的:delete from t_test20191023 where id not in (select minid from (select min(id) as minid from t_test20191023 group by name order by id) b)