删除2条完全一样的数据
今天百度知道上面,有看到一个帖,说要求:
2条完全一样的数据删除一条保留一条,用SQL语句删除。
SQL Server 的处理办法
-- 首先创建测试表
CREATE TABLE test_delete(
name varchar(10),
value INT
);
go
-- 测试数据,其中 张三100 与 王五80 是完全一样的
INSERT INTO test_delete
SELECT '张三', 100
UNION ALL SELECT '张三', 100
UNION ALL SELECT '李四', 80
UNION ALL SELECT '王五', 80
UNION ALL SELECT '王五', 80
UNION ALL SELECT '赵六', 90
UNION ALL SELECT '赵六', 70
go
-- 首先查询一下, ROW_NUMBER 效果是否满足预期
SELECT
ROW_NUMBER() OVER (PARTITION BY name, value ORDER BY (SELECT 1) ) AS no,
name,
value
FROM
test_delete
no name value
----- ---------- -----------
1 李四 80
1 王五 80
2 王五 80
1 张三 100
2 张三 100
1 赵六 70
1 赵六 90
从结果上可以看到,如果有重复的,完全一样的话, no 是有大于1的。
-- 创建视图
CREATE VIEW tmp_view AS
SELECT
ROW_NUMBER() OVER (PARTITION BY name, value ORDER BY (SELECT 1) ) AS no,
name,
value
FROM
test_delete
-- 删除 视图中的 no 不等于 1 的数据。
1> DELETE FROM tmp_view WHERE no != 1
2> go
(2 行受影响)
1>
2> select * from test_delete;
3> go
name value
---------- -----------
张三 100
李四 80
王五 80
赵六 90
赵六 70
(5 行受影响)
结果看上去是满足预期的。
Oracle 的处理办法
使用 Oracle 的 ROWID 来删除的处理步骤如下:
SQL> CREATE TABLE test_delete(
2 name varchar(10),
3 value INT
4 );
表已创建。
SQL> INSERT INTO test_delete
2 SELECT '张三', 100 FROM dual
3 UNION ALL SELECT '张三', 100 FROM dual
4 UNION ALL SELECT '李四', 80 FROM dual
5 UNION ALL SELECT '王五', 80 FROM dual
6 UNION ALL SELECT '王五', 80 FROM dual
7 UNION ALL SELECT '赵六', 90 FROM dual
8 UNION ALL SELECT '赵六', 70 FROM dual;
已创建7行。
SQL> SELECT
2 ROWID,
3 name,
4 value
5 FROM
6 test_delete;
ROWID NAME VALUE
------------------ ---------- ----------
AAAM2mAAGAAAAOXAAA 张三 100
AAAM2mAAGAAAAOXAAB 张三 100
AAAM2mAAGAAAAOXAAC 李四 80
AAAM2mAAGAAAAOXAAD 王五 80
AAAM2mAAGAAAAOXAAE 王五 80
AAAM2mAAGAAAAOXAAF 赵六 90
AAAM2mAAGAAAAOXAAG 赵六 70
已选择7行。
SQL> DELETE
2 test_delete
3 WHERE
4 (name, value)
5 IN (SELECT
6 name, value
7 FROM
8 test_delete
9 GROUP BY
10 name, value
11 HAVING COUNT(1) > 1)
12 AND rowid NOT IN
13 (SELECT
14 MIN(rowid)
15 FROM
16 test_delete
17 GROUP BY
18 name, value
19 HAVING
20 COUNT(1) > 1);
已删除2行。
SQL> SELECT
2 ROWID,
3 name,
4 value
5 FROM
6 test_delete;
ROWID NAME VALUE
------------------ ---------- ----------
AAAM2mAAGAAAAOXAAA 张三 100
AAAM2mAAGAAAAOXAAC 李四 80
AAAM2mAAGAAAAOXAAD 王五 80
AAAM2mAAGAAAAOXAAF 赵六 90
AAAM2mAAGAAAAOXAAG 赵六 70