一、背景
一张person表,有id和name的两个字段,id是唯一的不允许重复,id相同则认为是重复的记录。
二、解决
select id from group by id having count(*) > 1
按照id分组并计数,某个id号那一组的数量超过1条则认为重复。
如何查询重复的数据
1
|
select
字段1,字段2,
count
(*)
from
表名
group
by
字段1,字段2
having
count
(*) > 1
|
PS:将上面的>号改为=号就可以查询出没有重复的数据了。
Oracle删除重复数据的SQL(删除所有):
删除重复数据的基本结构写法:
想要删除这些重复的数据,可以使用下面语句进行删除
1
2
|
delete
from
表名 a
where
字段1,字段2
in
(
select
字段1,字段2,
count
(*)
from
表名
group
by
字段1,字段2
having
count
(*) > 1)
|
上面的SQL注意:语句非常简单,就是将查询到的数据删除掉。不过这种删除执行的效率非常低,对于大数据量来说,可能会将数据库吊死。
建议先将查询到的重复的数据插入到一个临时表中,然后对进行删除,这样,执行删除的时候就不用再进行一次查询了。如下:
CREATE TABLE 临时表 AS (select 字段1,字段2,count(*) from 表名 group by 字段1,字段2 having count(*) > 1)
上面这句话就是建立了临时表,并将查询到的数据插入其中。
下面就可以进行这样的删除操作了:
1
|
delete
from
表名 a
where
字段1,字段2
in
(
select
字段1,字段2
from
临时表);
|
Oracle删除重复数据
的SQL(留下一条记录):oracle中,有个隐藏了自动rowid,里面给每条记录一个唯一的rowid,我们如果想保留最新的一条记录,我们就可以利用这个字段,保留重复数据中rowid最大的一条记录就可以了。
使用ROWID查询重复数据:
1
2
3
4
5
|
select
a.rowid,a.*
from
表名 a
where
a.rowid !=
(
select
max
(b.rowid)
from
表名 b
where
a.字段1 = b.字段1
and
a.字段2 = b.字段2 )
|
括号中的SQL查询出rowid最大的记录,而外面就是查询出除了rowid最大之外的其他重复的数据了。
由此,我们要删除重复数据,只保留最新的一条数据,就可以这样写了:
删除重复数据(留下最大ROWID的一条)
1
2
3
4
|
delete
from
表名 a
where
a.rowid !=
(
select
max
(b.rowid)
from
表名 b
where
a.字段1 = b.字段1
and
a.字段2 = b.字段2 )
|
删除重复数据(留下最小ROWID的一条)
1
2
3
|
delete
tab t
where
t.rowid > (
select
min
(t2.rowid)
from
tab t2
where
t.col2 = t2.col2
and
t.col8 = t2.col8
)
|
当然,上面语句的执行效率是很低的,可以考虑建立临时表,讲需要判断重复的字段、rowid插入临时表中,然后删除的时候在进行比较。
1
2
3
4
5
6
7
|
create
table
临时表
as
select
a.字段1,a.字段2,
MAX
(a.ROWID) dataid
from
正式表 a
GROUP
BY
a.字段1,a.字段2;
delete
from
表名 a
where
a.rowid !=
(
select
b.dataid
from
临时表 b
where
a.字段1 = b.字段1
and
a.字段2 = b.字段2 );
commit
;
|
对于完全重复记录的删除
对于表中两行记录完全一样的情况,可以用下面语句获取到去掉重复数据后的记录:
1
|
select
distinct
*
from
表名
|
可以将查询的记录放到临时表中,然后再将原来的表记录删除,最后将临时表的数据导回原来的表中。如下:
1
2
3
4
|
CREATE
TABLE
临时表
AS
(
select
distinct
*
from
表名);
truncate
table
正式表;
insert
into
正式表 (
select
*
from
临时表);
drop
table
临时表;
|
如果想删除一个表的重复数据,可以先建一个临时表,将去掉重复数据后的数据导入到临时表,然后在从临时表将数据导入正式表中,如下:
1
2
|
INSERT
INTO
t_table_bak
select
distinct
*
from
t_table;
|
MySQL查询及删除重复记录的方法
查询及删除重复记录的方法(例子演示)
1、查找表中多余的重复记录,重复记录是根据单个字段(peopleId)来判断
1
|
select
*
from
table
where
tableId
in
(
select
tableId
from
table
group
by
tableId
having
count
(tableId) > 1)
|
2、删除表中多余的重复记录,重复记录是根据单个字段(tableId)来判断,只留有rowid最小的记录。
1
|
delete
from
table
where
tableId
in
(
select
tableId
from
table
group
by
tableId
having
count
(tableId) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
table
group
by
tableId
having
count
(tableId )>1)
|
3、查找表中多余的重复记录(多个字段)
1
|
select
*
from
vitae a
where
(a.tableId,a.seq)
in
(
select
tableId,seq
from
vitae
group
by
tableId,seq
having
count
(*) > 1)
|
4、删除表中多余的重复记录(多个字段),只留有rowid最小的记录
1
2
|
delete
from
vitae a
where
(a.tableId,a.seq)
in
(
select
tableId,seq
from
vitae
group
by
tableId,seq
having
count
(*) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
vitae
group
by
tableId,seq
having
count
(*)>1)
|
5、查找表中多余的重复记录(多个字段),不包含rowid最小的记录
1
|
select
*
from
vitae a
where
(a.tableId,a.seq)
in
(
select
tableId,seq
from
vitae
group
by
tableId,seq
having
count
(*) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
vitae
group
by
tableId,seq
having
count
(*)>1)
|
6、查询出一个表中,某一列的值是相同的SQL:
比方说
在A表中存在一个字段“name”,而且不同记录之间的“name”值有可能会相同,
现在就是需要查询出在该表中的各记录之间,“name”值存在重复的项;
1
|
Select
Name
,
Count
(*)
From
A
Group
By
Name
Having
Count
(*) > 1
|
如果还查性别也相同大则如下:
1
|
Select
Name
,sex,
Count
(*)
From
A
Group
By
Name
,sex
Having
Count
(*) > 1
|
oracle查询表中字段里数据是否有重复
查单个字段:
1
|
SELECT
TEST_NAME,
COUNT
(*)
FROM
T_TEST
GROUP
BY
TEST_NAME
HAVING
COUNT
(*) > 1
|
Oracle查询重复数据并删除,只保留一条记录
1、查找表中多余的重复记录,重复记录是根据单个字段(Id)来判断
1
2
3
|
select
*
from
表
where
Id
in
(
select
Id
from
表
group
byId
having
count
(Id) >
1)
|
2、删除表中多余的重复记录,重复记录是根据单个字段(Id)来判断,只留有rowid最小的记录
1
2
3
4
|
DELETE
from
表
WHERE
(id)
IN
(
SELECT
id
FROM
表
GROUP
BY
id
HAVING
COUNT
(id) > 1)
AND
ROWID
NOT
IN
(
SELECT
MIN
(ROWID)
FROM
表
GROUP
BY
id
HAVING
COUNT
(*) >
1);
|
3、查找表中多余的重复记录(多个字段)
1
2
3
|
select
*
from
表 a
where
(a.Id,a.seq)
in
(
select
Id,seq
from
表
group
by
Id,seq
having
count
(*) > 1)
|
4、删除表中多余的重复记录(多个字段),只留有rowid最小的记录
1
2
3
4
|
delete
from
表 a
where
(a.Id,a.seq)
in
(
select
Id,seq
from
表
group
by
Id,seq
having
count
(*) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
表
group
by
Id,seq
having
count
(*)>1)
|
5、查找表中多余的重复记录(多个字段),不包含rowid最小的记录
1
2
3
4
|
select
*
from
表 a
where
(a.Id,a.seq)
in
(
select
Id,seq
from
表
group
by
Id,seq
having
count
(*) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
表
group
by
Id,seq
having
count
(*)>1)
|
比如现在有一人员表 (表名:peosons)
若想将姓名、身份证号、住址这三个字段完全相同的记录查询出来
1
2
3
4
5
|
select
p1.*
from
persons p1,persons p2
where
p1.id<>p2.id
and
p1.cardid = p2.cardid
and
p1.pname = p2.pname
and
p1.address = p2.address
|
可以实现上述效果。
几个删除重复记录的SQL语句
1.用rowid方法
2.用group by方法
3.用distinct方法
1。用rowid方法
据据oracle带的rowid属性,进行判断,是否存在重复,语句如下:
查数据:
1
2
|
select
*
from
table1 a
where
rowid !=(
select
max
(rowid)
from
table1 b
where
a.name1=b.name1
and
a.name2=b.name2……)
|
删数据:
1
2
|
delete
from
table1 a
where
rowid !=(
select
max
(rowid)
from
table1 b
where
a.name1=b.name1
and
a.name2=b.name2……)
|
2.group by方法
查数据:
select count(num), max(name) from student
--列出重复的记录数,并列出他的name属性
group by num
having count(num) >1 --按num分组后找出表中num列重复,即出现次数大于一次
删数据:
1
2
3
|
delete
from
student
group
by
num
having
count
(num) >1
|
这样的话就把所有重复的都删除了。
3.用distinct方法 -对于小的表比较有用
1
2
3
4
|
create
table
table_new
as
select
distinct
*
from
table1
minux
truncate
table
table1;
insert
into
table1
select
*
from
table_new;
|
查询及删除重复记录的方法大全
1、查找表中多余的重复记录,重复记录是根据单个字段(peopleId)来判断
1
2
3
|
select
*
from
people
where
peopleId
in
(
select
peopleId
from
people
group
by
peopleId
having
count
(peopleId) > 1)
|
2、删除表中多余的重复记录,重复记录是根据单个字段(peopleId)来判断,只留有rowid最小的记录
1
2
3
4
5
6
|
delete
from
people
where
peopleId
in
(
select
peopleId
from
people
group
by
peopleId
having
count
(peopleId) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
people
group
by
peopleId
having
count
(peopleId )>1)
|
3、查找表中多余的重复记录(多个字段)
1
2
3
|
select
*
from
vitae a
where
(a.peopleId,a.seq)
in
(
select
peopleId,seq
from
vitae
group
by
peopleId,seq
having
count
(*) > 1)
|
4、删除表中多余的重复记录(多个字段),只留有rowid最小的记录
1
2
3
4
5
|
delete
from
vitae a
where
(a.peopleId,a.seq)
in
(
select
peopleId,seq
from
vitae
group
by
peopleId,seq
having
count
(*) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
vitae
group
by
peopleId,seq
having
count
(*)>1)
|
5、查找表中多余的重复记录(多个字段),不包含rowid最小的记录
1
2
3
4
5
|
select
*
from
vitae a
where
(a.peopleId,a.seq)
in
(
select
peopleId,seq
from
vitae
group
by
peopleId,seq
having
count
(*) > 1)
and
rowid
not
in
(
select
min
(rowid)
from
vitae
group
by
peopleId,seq
having
count
(*)>1)
|
(二)
比方说
在A表中存在一个字段“name”,
而且不同记录之间的“name”值有可能会相同,
现在就是需要查询出在该表中的各记录之间,“name”值存在重复的项;
1
2
|
Select
Name
,
Count
(*)
From
A
Group
By
Name
Having
Count
(*) >
1
|
如果还查性别也相同大则如下:
1
2
|
Select
Name
,***,
Count
(*)
From
A
Group
By
Name
,***
Having
Count
(*) > 1
|
(三)
方法一
1
2
3
4
5
6
7
8
9
10
11
12
13
14
|
declare
@
max
integer
,@id
integer
declare
cur_rows
cursor
local
for
select
主字段,
count
(*)
from
表名
group
by
主字段
having
count
(*) >; 1
open
cur_rows
fetch
cur_rows
into
@id,@
max
while @@fetch_status=0
begin
select
@
max
= @
max
-1
set
rowcount @
max
delete
from
表名
where
主字段 = @id
fetch
cur_rows
into
@id,@
max
end
close
cur_rows
set
rowcount 0
|
方法二
"重复记录"有两个意义上的重复记录,一是完全重复的记录,也即所有字段均重复的记录,二是部分关键字段重复的记录,
比如Name字段重复,而其他字段不一定重复或都重复可以忽略。
1、对于第一种重复,比较容易解决,使用
select distinct * from tableName就可以得到无重复记录的结果集。
如果该表需要删除重复的记录(重复记录保留1条),可以按以下方法删除
1
2
3
4
|
select
distinct
*
into
#Tmp
from
tableName
drop
table
tableName
select
*
into
tableName
from
#Tmp
drop
table
#Tmp
|
发生这种重复的原因是表设计不周产生的,增加唯一索引列即可解决。
2、这类重复问题通常要求保留重复记录中的第一条记录,操作方法如下
假设有重复的字段为Name,Address,要求得到这两个字段唯一的结果集
1
2
3
4
5
6
|
select
identity(
int
,1,1)
as
autoID, *
into
#Tmp
from
tableName
select
min
(autoID)
as
autoID
into
#Tmp2
from
#Tmp
group
by
Name
,autoID
select
*
from
#Tmp
where
autoID
in
(
select
autoID
from
#tmp2)
|
最后一个select即得到了Name,Address不重复的结果集(但多了一个autoID字段,实际写时可以写在select子句中省去此列)
(四)查询重复
1
2
3
4
5
|
select
*
from
tablename
where
id
in
(
select
id
from
tablename
group
by
id
having
count
(id) > 1
)
|
原文链接:http://www.cnblogs.com/qmfsun/p/4871776.html