方法1:
8 k8 u0 W, L( |' U0 x: ]/ j1、创建一个临时表,选取需要的数据。% V' B4 q( ]2 _7 r0 x, R/ r, Z! d% ?
2、清空原表。& S; y9 q% A. k6 ?/ y. O0 P1 ^$ v, n
3、临时表数据导入到原表。: @9 B6 K1 L, ^
4、删除临时表。
: b. M( Z. z$ I R. C9 S- nmysql> select * from student;% }2 ]; v0 x: T7 i
+----+------+: H- U3 l3 M) O
| ID | NAME |
2 t3 i" J9 P. Z! w( l4 K2 c+----+------+
6 q1 q2 f' p1 [6 Y1 M2 ~| 11 | aa |/ [4 T u: \1 B+ P7 P; O% B
| 12 | aa |
8 Q/ R! ^' ?+ P| 13 | bb |
2 Z2 B' k* Y% j! a1 ]/ x| 14 | bb |+ e7 `1 x c5 I5 i! K
| 15 | bb |3 ?$ h( |# q$ b8 a1 ?) e7 ~
| 16 | cc |
# R( P2 e1 \; E# h+----+------+
' R& E8 `/ v5 e! A9 M1 M6 rows in set mysql> create temporary table temp as select min(id),name from student group by name;
' o6 z7 G5 M. XQuery OK, 3 rows affected
$ j1 D& L: v+ j; L# q; y" h! e5 E4 TRecords: 3 Duplicates: 0 Warnings: 0 mysql> truncate table student;
) a V7 e5 o- z5 P* n( D7 O4 mQuery OK, 0 rows affected mysql> insert into student select * from temp;
z4 L( f, Y U% D$ X! rQuery OK, 3 rows affected% M S, J: N6 [, D
Records: 3 Duplicates: 0 Warnings: 0 mysql> select * from student;
* r7 E) G' J i3 ~- z+ V8 V+----+------+
9 T- d% {8 X$ L @$ X3 A6 x" T, J| ID | NAME |
% A4 d; R! x. |9 f+----+------+, k! I6 a' q4 W; [
| 11 | aa |
1 g6 G) x* p' @$ \. ^! e| 13 | bb |9 L: ^3 S* I9 ?9 z! d: \
| 16 | cc |+ l! }, q' |$ P2 Y- f
+----+------+' B1 E' W2 H( J! U1 S$ A8 k4 G% c% K
3 rows in set mysql> drop temporary table temp;
# U9 U# f' ?( i; ZQuery OK, 0 rows affected
7 \1 S" Q/ F( @. u8 B这个方法,显然存在效率问题。
方法2:按name分组,把最小的id保存到临时表,删除id不在最小id集合的记录,如下:
9 N8 e. K2 s8 M G1 H- @& k$ _0 o1 Dmysql> create temporary table temp as select min(id) as MINID from student group by name;
0 @4 B8 @' r n8 w4 o' i$ LQuery OK, 3 rows affected* C$ Z. g/ q6 H1 A v3 V
Records: 3 Duplicates: 0 Warnings: 0 mysql> delete from student where id not in (select minid from temp);
0 X4 I) @+ d0 h8 o% M* u# W+ i& }+ _Query OK, 3 rows affected mysql> select * from student;6 V3 ]/ O; i, I4 q* u7 _& \
+----+------+
, w, h7 X9 D9 o9 ]* K' |' z| ID | NAME |- D/ l5 q0 n4 ~' ?% z+ M/ i( ?! T
+----+------+
" b0 F; v0 j; Y9 ^. s| 11 | aa |' j% L% U# N/ t7 L- k& S9 e: A! `
| 13 | bb |
S9 ?0 [) D. m, C) k4 o/ || 16 | cc |$ Z+ P: n; C0 z* V! K1 W. j C
+----+------+0 y9 e3 h& z3 M. t
3 rows in set
方法3:直接在原表上操作,容易想到的sql语句如下: mysql> delete from student where id not in (select min(id) from student group by name);$ K$ C7 _ k1 k& ~/ O$ l, B6 R
执行报错:1093 - You can't specify target table 'student' for update in FROM clause1 _/ B d. @3 \8 n) u" L
原因是:更新数据时使用了查询,而查询的数据又做了更新的条件,mysql不支持这种方式。
6 D0 I' K) x( A8 f- y$ z怎么规避这个问题?3 Q+ O' W, b5 q& j
再加一层封装,如下:
0 Y4 j% q/ G+ k# p* o9 b4 _mysql> delete from student where id not in (select minid from (select min(id) as minid from student group by name) b);
$ o {8 {. g7 M8 q% Z" YQuery OK, 3 rows affected mysql> select * from student;
$ @; E( K+ ~9 g2 e; j! K+----+------+
+ W3 [0 ]& d8 ?4 v: ?3 p9 e( a: c| ID | NAME |& d% G: m7 [$ D9 N. c
+----+------+# z, N, [8 i v3 n: b% `
| 11 | aa |
: m8 G/ l& j1 Z* ~; s| 13 | bb |" U7 I" i# D" b/ L* m ?) g; `
| 16 | cc |
: r3 {- ~ T. F# m+----+------+
7 c, }7 p8 W0 R: y' C5 _3 rows in set * `$ t$ R& s* z2 G/ Y* \! w3 q
方法三例如:delete from bugdata where id not in (select minid from (select min(id) as minid from bugdata group by qxbh) b);
w' M+ p: Z: s" {: p0 S1 A0 P: [9 R4 E9 T
; y, `1 _. j6 R. m. V4 {# n1 w |