找回密码
 立即注册
欢迎中测联盟老会员回家,1997年注册的域名
查看: 1731|回复: 0
打印 上一主题 下一主题

mysql删除重复记录,保存Id最小的一条

[复制链接]
跳转到指定楼层
楼主
发表于 2016-8-23 20:58:17 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
方法1:6 S# T" d9 n/ L  i6 _! a
1、创建一个临时表,选取需要的数据。
7 V, x) z3 W/ \; l/ ~4 w3 k2、清空原表。+ M+ |/ W/ ~+ s0 w( `
3、临时表数据导入到原表。- \( j7 L! K$ W  W6 x. t& b
4、删除临时表。2 l7 r7 Q, t' i/ `
mysql> select * from student;
& C  C8 ?; @) ]3 E/ P+----+------+
& R4 F5 _; f+ u" Z5 ^% Z- |) t| ID | NAME |. Q" b3 ]$ H0 l  a) c  E/ p" t
+----+------+! L0 E  u/ P5 ]6 I7 ~- F0 H2 T
| 11 | aa |- Y" n8 z9 E) W! \6 d# V
| 12 | aa |% c' f4 ?9 p: |1 d+ s! H
| 13 | bb |, X9 e. l5 C( `: t/ L0 y
| 14 | bb |
% A1 d9 c5 F0 d7 j' ~* {- B| 15 | bb |; Y8 m5 K) P* x. c% A) I2 L% X$ Y
| 16 | cc |% E4 l- A1 u4 ~4 v& i& j1 F
+----+------+
. N7 X/ q, y' ^& f: C# n% s6 rows in set
mysql> create temporary table temp as select min(id),name from student group by name;  w; m1 ?! T! i. g% }# K7 c$ z
Query OK, 3 rows affected3 a! {  P& S$ c2 l! y; G
Records: 3 Duplicates: 0 Warnings: 0
mysql> truncate table student;$ R9 M. e. @- K# r! d( u' G5 ]
Query OK, 0 rows affected
mysql> insert into student select * from temp;7 o/ Q$ P' k* w
Query OK, 3 rows affected1 U  b9 l' _7 l$ `5 J! r# x
Records: 3 Duplicates: 0 Warnings: 0
mysql> select * from student;3 t! w1 P* O+ e/ E! D1 u! X7 b
+----+------+
, z0 b  n5 V4 s  R( I6 v| ID | NAME |3 n  C( C% B" j; Q* K- E* p
+----+------+5 p6 j% a5 v, w% y% n9 Z- I; a
| 11 | aa |
# s( q6 [, x; _) T) k3 x: M. i| 13 | bb |
1 e# l& c4 I& X- x/ X| 16 | cc |, e( @4 Z/ B; c6 [  f
+----+------+
( }% S1 A) k/ r! b1 v1 ?+ W3 rows in set
mysql> drop temporary table temp;! O+ z" l$ c& q6 O0 ?# r1 n1 W
Query OK, 0 rows affected
4 V4 s1 a0 F( z5 L  Y# V7 J这个方法,显然存在效率问题。

方法2:按name分组,把最小的id保存到临时表,删除id不在最小id集合的记录,如下:4 r/ ~( N  m  |- A9 O1 i- q6 }
mysql> create temporary table temp as select min(id) as MINID from student group by name;
8 s  y' f% e8 g8 F+ A7 `Query OK, 3 rows affected
7 l4 _7 {. g# g8 o# E- HRecords: 3 Duplicates: 0 Warnings: 0
mysql> delete from student where id not in (select minid from temp);
( `) V0 t4 w* a. Q8 G# QQuery OK, 3 rows affected
mysql> select * from student;: {6 f1 I* P4 s  {
+----+------+: j" _: J0 {: ?% t
| ID | NAME |
* ~: L7 [: g0 m# W+----+------+$ `) ^  X' ]3 w6 ?# \9 z; t
| 11 | aa |% n" R2 V  t, e2 d9 z$ o' k" @
| 13 | bb |
' F8 E9 E) S5 O$ F, \# B! e8 }" W| 16 | cc |
6 w* p* u( I, _* |$ }+----+------+  h# A7 D& s6 ~& ]; P
3 rows in set

方法3:直接在原表上操作,容易想到的sql语句如下:
mysql> delete from student where id not in (select min(id) from student group by name);9 R" V7 p& J2 w, a2 S3 K
执行报错:1093 - You can't specify target table 'student' for update in FROM clause
% u8 }( {3 Q  N$ T9 N$ w4 W& S原因是:更新数据时使用了查询,而查询的数据又做了更新的条件,mysql不支持这种方式。( w3 ?; W0 L5 _2 P9 V
怎么规避这个问题?# i6 O( b$ v3 ~' q! Q9 F. z
再加一层封装,如下:# N" \* l% o( Y! q
mysql> delete from student where id not in (select minid from (select min(id) as minid from student group by name) b);
( ~: K, u$ r; S; G. Q6 _5 {+ kQuery OK, 3 rows affected
mysql> select * from student;
2 P1 i8 H- [. Y. u" o5 G* i+----+------+4 ?( @( m0 n+ Q/ e8 c! C* E
| ID | NAME |* {5 ?. `, a, S# t: i9 a
+----+------+: l7 A% r* P5 L# d, `& r
| 11 | aa |
3 ~, p4 T; R0 ~8 [: K; j| 13 | bb |
/ C$ _0 h4 o# F. K2 p9 }3 I| 16 | cc |
+ x' G' |) c0 g+----+------+
9 @% y9 J# Q8 c6 q5 R$ `! i3 rows in set

) j* B5 O3 ^) l9 J# i: t方法三例如:delete from bugdata where id not in (select minid from (select min(id) as minid from bugdata group by qxbh) b);& |) }& G* H: t4 M9 Z

/ i1 e; d1 a) J5 p7 Y
* |) g% ^+ |* Q1 k9 O" N8 Z& X
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表