SQL删除重复的记录(只保留一条)-窗口函数row_number()

news2024/10/6 8:27:38

文章目录

  • 一、关于mysql表中数据重复
  • 二、聚合函数min(id)+not in
  • 二、窗口函数row_number()
  • 四、补充:常见的窗口函数

一、关于mysql表中数据重复

关于删除mysql表中重复数据问题,本文中给到两种办法:聚合函数、窗口函数row_number()的方法。
(注意:MySQL从8.0开始支持窗口函数)

测试数据准备:首先创建一个测试表test,插入一些测试数据,模拟一些重复数据(最终目标:删除重复数据,但不处理null行)

先查询下重复数据,确认待处理数据的数量,然后开始处理:

SELECT
        seq_id,
        out_user_code,
        COUNT( out_user_code ) count
FROM
        test
WHERE
        is_deleted = 0
        AND out_user_code IS NOT NULL
GROUP BY
        out_user_code
HAVING
        count( out_user_code )> 1

二、聚合函数min(id)+not in

思路:首先通过子查询取出 id 最小的不重复行,然后通过 not in 删除重复数据

1、首先查询一下 id 最小的不重复行(我们留下最早插入的数据,后面的重复数据都删除):

SELECT
    min(seq_id) seq_id,
	out_user_code,
	COUNT( out_user_code ) count 
FROM
	test 
GROUP BY
	out_user_code 

2、通过查询结果可知,重复的数据行seq_id为2、7的数据过滤掉了,接下来NOT IN 操作应该删除2、7重复数据行。那按照假设想法执行NOT IN:

DELETE from test where r.seq_id not in (
	SELECT
	min(t.seq_id) seq_id
	FROM
		test  t
	GROUP BY
		t.out_user_code
)  r

会发现报错:

1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'r' at line 8, Time: 0.007000s

原因:不能先select出同一表中的某些值,再update这个表(在同一语句中),即不能依据某字段值做判断再来更新某字段的值。

解决方案:可将SELECT出的结果再通过中间表SELECT一遍。

3、最终处理sql:

DELETE from test where seq_id not in (
	SELECT r.seq_id from (
		SELECT
		   min(t.seq_id) seq_id
		FROM
			test  t
		GROUP BY
			t.out_user_code
	)  r 
) and out_user_code is not null

换种写法(保证相关字段有索引):

DELETE from test 
where
out_user_code in (select * from (select out_user_code from test del group by out_user_code HAVING count(out_user_code) >1)a)
and seq_id not in(select * from (select min(seq_id) id from test del group by out_user_code  HAVING count(out_user_code) >1)b
)f

提醒:能逻辑删除尽量不要物理删除。

二、窗口函数row_number()

思路:通过 PARTITION BY 对列进行分区排序并生成序号列,然后将序号大于 1 的行删除,row_number() over partition by。

1、分区查询:

SELECT
	ROW_NUMBER() OVER ( PARTITION BY out_user_code ORDER BY seq_id ) num,
	out_user_code 
FROM
	test 
WHERE
	out_user_code IS NOT NULL

知识补充:
1、ROW_NUMBER:对结果集的输出进行编号,是运行查询时计算出的临时值。 具体来说,返回结果集分区内行的序列号,每个分区的第一行从 1 开始。
2、ROW_NUMBER() 具有不确定性。除非以下条件成立,否则不保证在每次执行时,使用 ROW_NUMBER() 的查询所返回行的顺序都完全相同。
1)分区列的值是唯一的。
2)ORDER BY 列的值是唯一的。
3)分区列和 ORDER BY 列的值的组合是唯一的。

2、直接尝试删除num>1的数据:

DELETE a 
FROM (
	SELECT
	 ROW_NUMBER() OVER (PARTITION BY out_user_code ORDER BY seq_id) num 
	FROM test 
	where out_user_code IS NOT NULL
) a 
WHERE num>1

会发现报错:
1288 - The target table a of the DELETE is not updatable, Time: 0.007000s

原因同上,同样的我们换个方式处理一下。给窗口指定别名:WINDOW w AS (PARTITION BY 字段1 ORDER BY 字段2)

3、最终处理sql:

DELETE
FROM test
WHERE seq_id in (
	SELECT seq_id
	FROM(
		SELECT *
		FROM (
			SELECT ROW_NUMBER() OVER w AS row_num,seq_id
			FROM test  where out_user_code is not null
			WINDOW w AS (PARTITION BY out_user_code ORDER BY seq_id)
		)t
	    WHERE row_num >1
	)e
)

四、补充:常见的窗口函数

注:‘参数’列说明该函数是否可以加参数。“否”说明该函数的括号内不可以加参数。
expr即可以代表字段,也可以代表在字段上的计算,比如sum(col)等。

窗口函数的一个概念是当前行,当前行属于某个窗口,窗口由over关键字用来指定函数执行的窗口范围,如果后面括号中什么都不写,则意味着窗口包含满足where条件的所有行,窗口函数基于所有行进行计算;如果不为空,则有三个参数来设置窗口:

  • partition by子句:按照指定字段进行分区,两个分区由边界分隔,窗口函数在不同的分区内分别执行,在跨越分区边界时重新初始化。
  • order by子句:按照指定字段进行排序,窗口函数将按照排序后的记录顺序进行编号。可以和partition by子句配合使用,也可以单独使用。
  • frame子句:当前分区的一个子集,用来定义子集的规则,通常用来作为滑动窗口使用。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/539876.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

ffmpeg-mpv配置详解04

mpv.conf 格式详解 存放位置 windows下 Roaming\mpv linux下在.conf/mpv # mpv conf ################################################################################ # 记忆播放[退出时记住播放状态、音量、播放速度、位置等] save-position-on-quit # 播放状态保存位置…

运行时栈帧结构与方法调用

1 运行时栈帧结构 Java虚拟机以方法作为最基本执行单元,“栈帧”则是用于支持虚拟机进行方法调用和方法执行背后的数据结构。栈帧存储了方法的局部变量表、操作数栈、动态连接和方法返回地址等信息。 1.1 局部变量表 局部变量表的容量以变量槽为最小单位。 Java…

强化学习:贝尔曼方程(Bellman Equation)

∗ ∗ 重点:状态值、贝尔曼方程 ∗ ∗ **重点:状态值、贝尔曼方程** ∗∗重点:状态值、贝尔曼方程∗∗ return评估策略 在前面概念介绍中,我们知道了可以用 return 来评估一个策略的好坏。如图,有三个不同的策略&…

线性插值提高DDS相位分辨率

DDS(Direct Digital Synthesizer)即直接数字频率合成技术,主要由正弦查找表与控制器组成,通过控制器给出的相位,在正弦查找表中查找对应的正余弦值并予以输出。通过多个 DDS 信号的组合,可以进一步构建出 A…

【源码解析】Disruptor框架的源码解析

Disruptor初始化 初始化Disruptor实例 //单线程模式&#xff0c;获取额外的性能 Disruptor<MessageModel> disruptor new Disruptor<>(factory, bufferSize, executor,ProducerType.SINGLE, new BlockingWaitStrategy());创建RingBuffer实例 Deprecatedpublic D…

Midjourney|文心一格prompt教程[Text Prompt(上篇)]:品牌log、App、徽章、插画、头像场景生成,各种风格选择:科技风、运动风

Midjourney|文心一格prompt教程[Text Prompt&#xff08;上篇&#xff09;]&#xff1a;品牌log、App、徽章、插画、头像场景生成&#xff0c;各种风格选择&#xff1a;科技风、运动风 1.撰写 Text Prompt 注意事项 Midjourney 跟 ChatGPT 在 prompt 的使用上有很多不一样的地…

怎么做好媒体邀约

传媒如春雨&#xff0c;润物细无声&#xff0c;大家好 要做好媒体邀约&#xff0c;以下是一些关键步骤和建议&#xff1a; 1. 制定媒体邀约方案&#xff1a;首先&#xff0c;确定您希望邀约的目标媒体。了解他们的受众、内容定位和报道风格&#xff0c;确保与您的品牌和目标受众…

ChatGPT 的工作原理:深入探究

本文首发于微信公众号&#xff1a;大迁世界, 我的微信&#xff1a;qq449245884&#xff0c;我会第一时间和你分享前端行业趋势&#xff0c;学习途径等等。 更多开源作品请看 GitHub https://github.com/qq449245884/xiaozhi &#xff0c;包含一线大厂面试完整考点、资料以及我的…

opencv实践项目-图片拼接之缝合线算法

目录 1. stitcher_detail执行过程2. 源码3. stitching_detail 程序接口介绍4. 执行5. 结果图 1. stitcher_detail执行过程 stitcher_detail是opencv官网提供的一个用于多福图像拼接的Demo&#xff0c;其主要过程如下&#xff1a; 1.输入待拼接图像集合&#xff1b;2.分别对每幅…

Jetson Nano调试记录:机电设备控制

边缘应用中,机电控制是一项非常重要的能力。 当我们的智能设备在远端环境中,根据所识别的状况变化去执行应对措施,更大程度度地降低对人为操作的依赖,这些都是能产生更大经济效益的应用,包括无人驾驶车、自动机械手臂等等。 实际工业应用场景中的控制元件是非常多样化的,…

惠普暗影精灵5 super 873-068rcn怎样用u盘重装系统win10

当我们的戴尔电脑出现问题的时候&#xff0c;无法进入系统要怎么重装系统win10修复呢?比较常用的就是借助u盘重装系统win10&#xff0c;需要用到装机工具。下面就给大家详细介绍下戴尔电脑怎样用u盘重装系统win10教程。 工具/原料&#xff1a; 系统版本&#xff1a;windows1…

LSTM-理解 Part-3(LSTM Networks)

之前博客中有涉及前两部分的介绍&#xff1a; 第一部分LSTM-理解 Part-1&#xff08;RNN&#xff1a;循环神经网络&#xff09; 第二部分LSTM-理解 Part-2&#xff08;RNN的局限性&#xff09; 这是其中的第三部分&#xff0c;讲解 LSTM Networks。 LSTM Networks 长短期记忆网…

【Python MySQL】零基础也能轻松掌握的学习路线与参考资料

Python是一种广泛使用的编程语言&#xff0c;MySQL是一个流行的关系数据库管理系统。学习Python和MySQL可以帮助开发人员更有效地处理数据&#xff0c;并构建可扩展和强大的Web应用程序。本文将介绍Python MySQL学习路线&#xff0c;参考资料和优秀实践。 Python MySQL学习路线…

美的智家、海尔智家,吹响新一轮AI竞赛号角

ChatGPT大行其道&#xff0c;各行各业迫不及待披上了AI大模型的“盔甲”&#xff0c;有的企业自研AI大模型&#xff0c;有的企业牵手头部科技企业&#xff0c;寻求智能产品价值的最大化&#xff0c;智能家电行业也不例外。 在国内&#xff0c;百度AI大模型文心一言一经推出就吸…

卷绕模型介绍

卷绕模型是收放卷应用的基础知识,这篇博客帮大家整理分析,有关收放卷的其它相关基础知识请参看专栏相关文章。和这篇文章相关联的知识点大家可以参看下面的博客 体积法计算卷径详细介绍 卷径计算详解(通过卷绕的膜长和膜厚进行计算)_RXXW_Dor的博客-CSDN博客有关卷绕+张力控…

LoRA:大模型的低秩自适应微调模型

对于大型模型来说&#xff0c;重新训练所有模型参数的全微调变得不可行。比如GPT-3 175B&#xff0c;模型包含175B个参数吗&#xff0c;无论是微调训练和模型部署&#xff0c;都是不可能的事。所以Microsoft 提出了低秩自适应(Low-Rank Adaptation, LoRA)&#xff0c;它冻结了预…

企业级体验:未来体验管理的价值与趋势

我从事企业级体验相关领域的工作已十六载有余&#xff0c;曾经就职的企业既有阿里巴巴、腾讯这样的互联网“大厂”&#xff0c;也有顺丰、龙湖这样的线下“传统”企业。在这些企业中&#xff0c;我所工作的场景横跨了软件、电商、互联网、物流、零售、地产、金融等诸多业务领域…

11.计算机基础-计算机网络面试题—基础知识

本文目录如下&#xff1a; 计算机基础-计算机网络 面试题一、基础知识简述 TCP 和 UDP 的区别&#xff1f;http 与 https的区别?Session 和 Cookie 有什么区别&#xff1f;详细描述一下 HTTP 访问一个网站的过程&#xff1f;https 是如何实现加密的&#xff1f;URL是什么&…

Linux下网络编程(3)——socket编程实战,如何构建一个服务器和客户端连接

经过前几篇的介绍&#xff0c;本文我们将进行编程实战&#xff0c;实现一个简单地服务器和客户端应用程序。 编写服务器程序 编写服务器应用程序的流程如下&#xff1a; ①、调用 socket()函数打开套接字&#xff0c;得到套接字描述符&#xff1b; ②、调用 bind()函数将套接字…

Deep Supervised Dual Cycle Adversarial Network for Cross-Modal Retrieval 论文阅读笔记

​# 1. 论文信息 论文名称Deep Supervised Dual Cycle Adversarial Network for Cross-Modal Retrieval作者Lei Liao 中山大学会议/出版社IEEE Transactions on Circuits and Systems for Video Technologypdf&#x1f4c4;在线pdf代码&#x1f4bb;无代码 本文是基于公共空间…