如何查找和删除数据库中的重复数据

如何查找和删除数据库中的重复数据,第1张

如何查找和删除数据库中的重复数据

以Excel2010版本为例,可以直接使用数据→删除重复项的功能来实现删除重复数据。

此功能Excel2007及以上版本均可,WPS中也有这样的功能。另外还可以使用公式法去重复,常用的函数是Countif函数。

SQL数据库中, DISTINCT表示去掉重复的行,作用是针对包含重复值的数据表,用于返回唯一不同的值。语法是SELECT DISTINCT 列名称 FROM 表名称。如果指定了 SELECT DISTINCT,那么 ORDER BY 子句中的项就必须出现在选择列表中,否则会出现错误。

对于 DISTINCT关键字,如果后面有多个字段,则代表着是多条件去重,只有当这几个条件都相同时才算是重复记录。

扩展资料:

用法说明如下:

SELECT DISTINCT 列名称 FROM 表名称使用 DISTINCT 关键词

如果要从 "Company" 列中选取所有的值,需要使用 SELECT 语句:

SELECT Company FROM Orders"Orders"表:

Company OrderNumber

IBM 3532

W3School 2356

Apple 4698

W3School 6953

结果

Company

IBM

W3School

Apple

W3School

尽管DISTINCT用于过滤重复记录。 但是通常在使用时,仅使用其来返回唯一记录的数量,而不是使用其来返回非重复记录的所有值。 原因是DISTINCT只能通过双循环查询来解决,这无疑将直接影响具有大量数据的站点的效率。

易语言edb数据库能去重复。易语言edb数据库去重复的步骤如下:

1、易语言新建程序,新建一个Windows窗口程序,

2、添加精易模块,

3、输入命令文本:去重复文本(“1233546548732”,“”),

4、调试运行一下看下效果。

方法一

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条),可以按以下方法删除

select distinct into #Tmp from tableName

drop table tableName

select into tableName from #Tmp

drop table #Tmp

发生这种重复的原因是表设计不周产生的,增加唯一索引列即可解决。

2、这类重复问题通常要求保留重复记录中的第一条记录, *** 作方法如下:

假设有重复的字段为Name,Address,要求得到这两个字段唯一的结果集

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子句中省去此列)

问题背景

在一个多表查询的sql中正常情况下产生的数据都是唯一的,但因为数据库中存在错误(某张表中存在相同的外键ID)导致我这边查询出来的数据就会有重复的问题

下面结果集中UserID:15834存在多个

查询Sql如下:

SELECT FROM (SELECT ROW_NUMBER() OVER ( ORDER BY TUSERID asc )AS Row

,TUSERID

,TCreateTimeFROM UserInfo TLEFT JOIN DiseaseInfo i ON iUserID=TUserID

) TT WHERE TTRow between 0 AND 20 ORDER BY UserID DESC

解决方法:

参考下面新的解决方案

在网络上了解到MSSql中通过关键字“PARTITION BY”可以将查询结果集进行分区处理,然后在查询结果集时就可以过滤掉重复的记录了(如果有指定分区字段则区ID相同)

通过更改后的Sql,在Over中添加PARTITION BY TUSERID以UserID进行分区,然后在查询结果集时通过DISTINCT ROW ,过滤掉重复的分区ID号

SELECT DISTINCT ROW ,FROM (SELECT ROW_NUMBER() OVER (PARTITION BY TUSERID ORDER BY TUSERID asc )AS Row

,TUSERID

,TCreateTimeFROM UserInfo TLEFT JOIN DiseaseInfo i ON iUserID=TUserID

) TT WHERE TTRow between 0 AND 12 ORDER BY UserID DESC

查询时未过滤重复分区IDDISTINCT ROW ,下面的结果集跟上面的结果集不同(Row是进行过分区的所有有重复Row)

 

在查询结果集时过滤掉重复的分区ID号 DISTINCT ROW ,

新解决方案:

由于在Sqlserver中如果多表联合查询中除非所有的字段都完全相同否则在使用DISTINCT 用进行去重时还是会当成两个不同的数据集进行处理,因此DISTINCT会失效即

如下面的结果集,虽然 USERID和其他字段内容相同但HID是不相同的所以无法使用DISTINCT进行去重

出现这种问题是因为数据库设计的错误(正常情况下关联表HospitalInfo中只可能存在一条ClinicInfo表对应的记录)

Sql语句:

SELECT FROM (SELECT ROW_NUMBER() OVER ( order by TUSERID asc )AS Row

,TUSERID

,LEFT(TPatient_Tel1,5)+'00000000' AS Tel

,TCreateTime

,hHName

,hHID

fromUserInfo TLEFT JOIN ClinicInfo c ON cUserID=TUserID AND CDisabled=1LEFT JOIN HospitalInfo H ON HHID=cVisitHospital WHERE TDisabled=1AND tUserID>=17867 AND TUserID<=17875--(TPatient_Tel1 like '%13800000000%')) TT WHERETTRow between 0and20

可以看到上面的结果集中Row是有重复的,其他Row为2的是跟第一个是重复的

因为数据库涉及到其他业务和人员因此我只能提交该问题给相关的技术,但在该问题解决前不能影响到我这边也出现此问题

于是在原sql基础上进行处理,虽然HospitalInfo表中不重复记录但表的自增ID是不可能重复的那我只需要最新的一条记录即可

如果通过DISTINCT过进行去重则就无法成功,因为数据存在差别,可以看到第一条和最后一条数据还是重复的

SELECT DISTINCT row,FROM (SELECT ROW_NUMBER() OVER ( partition by TUSERID order by TUSERID asc )AS Row

,TUSERID

,LEFT(TPatient_Tel1,5)+'00000000' AS Tel

,TCreateTime

,hHName

,hHID

fromUserInfo TLEFT JOIN ClinicInfo c ON cUserID=TUserID AND CDisabled=1LEFT JOIN HospitalInfo H ON HHID=cVisitHospital WHERE TDisabled=1AND tUserID>=17867 AND TUserID<=17875--(TPatient_Tel1 like '%13800000000%')) TT WHERE--row=1 ANDTTRow between 0 and 20

更改后的Sql

SELECT FROM (--partition by TUSERID 以UserID对结果集进行分区SELECT ROW_NUMBER() OVER ( partition by TUSERID order by TUSERID asc )AS Row

,TUSERID

,LEFT(TPatient_Tel1,5)+'00000000' AS Tel

,TCreateTime

,hHName

,hHID

fromUserInfo TLEFT JOIN ClinicInfo c ON cUserID=TUserID AND CDisabled=1LEFT JOIN HospitalInfo H ON HHID=cVisitHospital WHERE TDisabled=1AND tUserID>=17867 AND TUserID<=17875--(TPatient_Tel1 like '%13800000000%')) TT WHERE--因为之前已经以UserID对结果集进行分区,所以如果存在重复的字段则row的值会不相同--row=1 ANDTTRow between 0 and 20

USERID=17867相同经过分区后会存在不同的Row值

在对结果集再次过滤时添加条件 : row=1,已经将重复记录中旧的数据过滤掉了 (HID:78)

根据新的解决方案解决了重复的问题,但又出现的新的问题即Row分区后都是重复的,而我再进行分页的时候就无效了(因为此时结果集中的Row都是为1)

解决方案:在结果集再加一层查询并加上ID号然后再对结果集进行分页处理

-- 新增一层查询解决过滤掉重复数据后无法分页的问题SELECT FROM (SELECT ROW_NUMBER() OVER (ORDER BY userid) AS RowNum,FROM (--partition by TUSERID 以UserID对结果集进行分区SELECT ROW_NUMBER() OVER ( partition by TUSERID order by TUSERID asc )AS Row

,TUSERID

,LEFT(TPatient_Tel1,5)+'00000000' AS Tel

,TCreateTime

,hHName

,hHID

fromUserInfo TLEFT JOIN ClinicInfo c ON cUserID=TUserID AND CDisabled=1LEFT JOIN HospitalInfo H ON HHID=cVisitHospital WHERE TDisabled=1AND tUserID>=17867 AND TUserID<=20875--(TPatient_Tel1 like '%13800000000%')) TT

)AS TWHERE--过滤重复数据Row=1--对结果进行分页AND RowNum between 13 and 24

参考:

MSDN: OVER 子句 (Transact-SQL)

stackoverflow sql query distinct with Row_Number

SQL Trick: row_number() is to SELECT what dense_rank() is to SELECT DISTINCT

以上就是关于如何查找和删除数据库中的重复数据全部的内容,包括:如何查找和删除数据库中的重复数据、数据库中 DISTINCT 的作用是什么、易语言edb数据库能去重复吗等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/sjk/9805388.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-05-02
下一篇 2023-05-02

发表评论

登录后才能评论

评论列表(0条)

保存