准备基础数据

(1)创建辅助表,方便以后倾向于Set-base方式解决问题

-- Creating and Populating the Nums Auxiliary Table
SET NOCOUNT ON;
IF OBJECT_ID('dbo.Nums', 'U') IS NOT NULL
DROP TABLE dbo.Nums; CREATE TABLE dbo.Nums(n INT NOT NULL PRIMARY KEY); DECLARE @max AS INT ,
@rc AS INT; SET @max = 1000000;
SET @rc = 1; INSERT INTO dbo.Nums
( n )
VALUES ( 1 );
WHILE @rc * 2 <= @max
BEGIN
INSERT INTO dbo.Nums
( n )
SELECT n + @rc
FROM dbo.Nums;
SET @rc = @rc * 2;
END
INSERT INTO dbo.Nums
( n
)
SELECT n + @rc
FROM dbo.Nums
WHERE n + @rc <= @max;
GO

(2) 准备一些重复数据,这里使用AdventureWorks2014

PS:造成重复数据的原因有很多种,比如没有设置主键,批量导入的时候可能被执行了多次,归根到底还是人为原因。

USE AdventureWorks2014;
GO IF OBJECT_ID('dbo.OrdersDups') IS NOT NULL
BEGIN
DROP TABLE dbo.OrdersDups;
END SELECT SalesOrderID ,
CustomerID ,
SalesPersonID ,
OrderDate
INTO dbo.OrdersDups
FROM Sales.SalesOrderHeader
CROSS JOIN dbo.Nums
WHERE n <= 3;

如图,我们有了许多重复数据,现在就要考虑如何去重了。

解决方案

这里小陈提供三种去重方案,每一种方案都有相似性,也有独特之处。

1. 使用ROW_NUMBER() 函数去重,这种方式适合于比例小的重复数据。

USE AdventureWorks2014;
GO WITH Dups AS (
SELECT SalesOrderID ,
CustomerID ,
SalesPersonID ,
OrderDate ,
ROW_NUMBER() OVER ( PARTITION BY SalesOrderID ORDER BY ( SELECT0) ) AS rn
FROM dbo.OrdersDups) DELETE FROM Dups
WHERE rn > 1;

在未删除之前,先看一下前10行的数据是什么模样.

2. 使用ROW_NUMBER() + RANK() 函数去重,这种方式跟第一种类似,也是适合比例小的重复数据。

USE AdventureWorks2014;
GO WITH Dups AS (
SELECT SalesOrderID ,
CustomerID ,
SalesPersonID ,
OrderDate ,
ROW_NUMBER() OVER ( PARTITION BY SalesOrderID ORDER BY ( SELECT 0) ) AS rn,
RANK() OVER(PARTITION BY SalesOrderID ORDER BY (SELECT 0)) AS rnk
FROM dbo.OrdersDups) DELETE FROM Dups
WHERE rn > 1;

3. 删除大量的重复行时,会导致日志行为,最终DELETE会执行的很慢。所以这里推荐的做法是复制唯一行到新表,减少日志操作。然后移除老表,把新表的名字重命名为老表。

USE AdventureWorks2014;
GO WITH Dups AS (
SELECT SalesOrderID ,
CustomerID ,
SalesPersonID ,
OrderDate ,
ROW_NUMBER() OVER ( PARTITION BY SalesOrderID ORDER BY ( SELECT 0) ) AS rn
FROM dbo.OrdersDups) SELECT
SalesOrderID ,
CustomerID ,
SalesPersonID ,
OrderDate
INTO dbo.OrdersDupsTmp
FROM Dups
WHERE rn = 1; DROP TABLE dbo.OrdersDups; EXEC sp_rename 'dbo.OrdersDupsTmp', 'OrdersDups';

总结

这篇主要讲述如何去重,作为T-SQL私房菜的开篇,也是作为学习T-SQL的笔记——记述常见问题的解决方案。

如何哪位看官对T-SQL解决常见问题有什么好的解决方案也可以提出来,小陈争取在T-SQL私房菜系列中做一个汇总,也方便以后遇到类似的问题时直接在这里借用了。

当然内功心法还是记在心里面最好,这也是应随了老话:烂笔头胜过好记性。

T-SQL Recipes之删除重复行的更多相关文章

  1. SQL Server删除重复行的6个方法

    SQL Server删除重复行是我们最常见的操作之一,下面就为您介绍六种适合不同情况的SQL Server删除重复行的方法,供您参考. 1.如果有ID字段,就是具有唯一性的字段 delect   ta ...

  2. SQL查找删除重复行

    本文讲述如何查找数据库里重复的行.这是初学者十分普遍遇到的问题.方法也很简单.这个问题还可以有其他演变,例如,如何查找“两字段重复的行”(#mysql IRC 频道问到的问题) 如何查找重复行 第一步 ...

  3. Oracle删除重复行

    Oracle删除重复行 分类: ORACLE2010-12-12 17:10 423人阅读 评论(0) 收藏 举报 oracletabledeleteintegerinsert.net 查询及删除重复 ...

  4. SqlServer_删除重复行只保留一条记录

      前提:相同的数据重复往数据库写入,导致存在仅主键Id不同的重复数据,现在需要去除重复数据,仅保留重复数据中Id最大的一条   思路: 1.找出存在重复数据的记录,并取重复数据中最大的Id值 2.删 ...

  5. linux用命令删除重复行

    文本处理时,经常要删除重复行,下面是三种方法 第一,用sort+uniq,注意,单纯uniq是不行的. sort -n test.txt | uniq 第二,用sort+awk命令,注意,单纯awk同 ...

  6. Sublime文本排序&查找重复行&删除重复行

    排序 按F9或者选择菜单:Edit > Sort Lines,对每行文本进行排序 查找重复行 排序好后,按Ctrl+F,调出查找面板 查找字符串: ^(.+)$[\r\n](^\1$[\r\n] ...

  7. editplus批量删除重复行(编辑-删除-删除重复行)

    editplus快速删除重复数据 多行文本,有些行的文字或数据是重复的,该怎么删除重复部分,只留下不重复的部分?很多人对这个问题感到无比头疼,Editplus同样能快速帮你删除数据. 那么,editp ...

  8. UE如何去除重复行,删除重复行

    1 如图所示,原理一个文本文档有两千多行,但是有大量的重复 2 使用UE的排序功能,有删除重复行的选项. 3 处理之后只剩下不到两百行了.

  9. Linux删除重复行

    本文转自http://blog.csdn.net/ithomer/article/details/6926325 文本处理时,经常要删除重复行,下面是三种方法 第一,用sort+uniq,注意,单纯u ...

随机推荐

  1. php操作mongodb

    <?php set_time_limit(0); $mongo = new Mongo('192.168.33.50:27017'); //连接远程主机22011端口 $db = $mongo- ...

  2. Python之路【第一篇】:Python简介和入门

    python简介: 一.什么是python Python(英国发音:/ pa θ n/ 美国发音:/ pa θɑ n/),是一种面向对象.直译式的计算机程序语言. 每一门语言都有自己的哲学: pyth ...

  3. c# 网络

    http://www.cnblogs.com/fuchongjundream/p/4079128.html http://stackoverflow.com/questions/21728773/th ...

  4. 2013成都网络赛 J A Bit Fun(水题)

    A Bit Fun Time Limit: 5000/2500 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total S ...

  5. thinkphp3.2.3之自动完成的实现

    有时候,我们希望系统能够帮我们自动完成一些功能,比如自动为密码加密,忽略空等,这个时候我们就需要利用到自动完成(填写)的功能. ThinkPHP 模型层提供的数据处理方法,主要用于数据的自动处理和过滤 ...

  6. OpenVPN使用用户名/密码验证方式

    OpenVPN推荐使用证书进行认证,安全性很高,但是配置起来很麻烦.还好它也能像pptp等vpn一样使用用户名/密码进行认证. 不管何种认证方式,服务端的ca.crt, server.crt, ser ...

  7. iOS开发——高级篇——通讯录

    一.简介 1.如何访问用户的通讯录1)在iOS9之前有2个框架可以访问用户的通讯录AddressBookUI.framework提供了联系人列表界面.联系人详情界面.添加联系人界面等一般用于选择联系人 ...

  8. Android多线程通信机制

    掌握Android的多线程通信机制,我们首先应该掌握Android中进程与线程是什么. 1. 进程 在Android中,一个应用程序就是一个独立的进程(应用运行在一个独立的环境中,可以避免其他应用程序 ...

  9. javascript——三元操作符

    {{C?A:B}} C条件成立则为A,不存在取B 比如在跟后台交互时,有许多要设默认值 <script type=''text/javascript> var value = docume ...

  10. 常用mysql语句

    mysql基本知识:日志文件 =======================================开启/关闭日志修改 /etc/my.cnf #log-bin=mysql-bin #重启my ...