我的编程空间,编程开发者的网络收藏夹
学习永远不晚

mysql清理重复数据,并保留最新一条

短信预约 -IT技能 免费直播动态提醒
省份

北京

  • 北京
  • 上海
  • 天津
  • 重庆
  • 河北
  • 山东
  • 辽宁
  • 黑龙江
  • 吉林
  • 甘肃
  • 青海
  • 河南
  • 江苏
  • 湖北
  • 湖南
  • 江西
  • 浙江
  • 广东
  • 云南
  • 福建
  • 海南
  • 山西
  • 四川
  • 陕西
  • 贵州
  • 安徽
  • 广西
  • 内蒙
  • 西藏
  • 新疆
  • 宁夏
  • 兵团
手机号立即预约

请填写图片验证码后获取短信验证码

看不清楚,换张图片

免费获取短信验证码

mysql清理重复数据,并保留最新一条

背景

之前,数据是通过表单提交
后来增加了excel批量导入的功能,但是这个接口没有判断数据重复,覆盖更新
导致线上环境出现大量重复数据
如果要保证数据库不出现重复数据,可以添加唯一索引来限制

参考:Mysql重复数据查重保留一条(id自增)

  • 只适合id自增的表,我的表id是uuid,所以需要借助其他的手段实现min函数
-- 连表删除delete t_userfrom t_user,(SELECT   min(id) id,   username  FROM   t_user  GROUP BY   username  HAVING   count(*) > 1) t2where t_user.username = t2.username-- 删除重复的比最小id大的数据,即保留id最小的那条数据and t_user.id > t2.id

改造:主键为uuid

  • 数据唯一判断,4个字段确定一条记录:type产品类型,name产品名称,customer客户,year_month年月
  • created_time 创建时间,据此排序分辨新旧

简单版

  • 一次清除每组一条重复数据,需要多执行几次,适合数据量少的情况
-- 每次都是取的最早的id-- 多执行几次DELETE from test_table_02 where id in (SELECT SUBSTRING_INDEX(ids, ',', 1) id from (select GROUP_CONCAT(id ORDER BY created_time) ids, type, name, customer, `year_month`, count(1) c from test_table_02 GROUP BY type, name, customer, `year_month`having c > 1) aaaa)
  • GROUP_CONCAT(id ORDER BY created_time) 聚合每组id,并根据创建时间正序,第一个即为最早的。倒序,则第一个为最新的。
  • SUBSTRING_INDEX(ids, ',', 1) 截取第一个id

扩展:截取第一个id的2种方式

方式1:使用SUBSTRING_INDEX() 函数
set @ids = '12,3,4,5,6';-- SUBSTRING_INDEX() 函数返回一个字符串中指定分隔符出现在指定次数【之前】的子字符串-- SUBSTRING_INDEX(str, delim, count)-- 从头开始,截取到第几个分隔符select SUBSTRING_INDEX(@ids, ',', 1); -- 12select SUBSTRING_INDEX(@ids, ',', 2); -- 12,3
方式2:INSTR() 和 LEFT() 函数结合
set @ids = '12,3,4,5,6';-- INSTR() 函数返回一个子字符串在一个字符串中【第一次】出现的位置的数字索引。 -- INSTR() 函数是不区分大小写的。-- 与java不同,下标从1开始,即为到这个字符位置的字符串长度select INSTR(@ids,','); -- 3-- LEFT() 函数从指定字符串的左侧 返回指定数量的字符组成的字符串。-- LEFT(string, length)-- 从头开始,截取指定长度select left(@ids, INSTR(@ids,',')-1); -- 12

加强版:一次性全部删除

select a.id from test_table_02 aINNER JOIN (select ids from(-- 保留第一个 截取第2个到最后一个idselect SUBSTR(ids,INSTR(ids,',')+1) ids from (-- 保留最后一个 截取第1个到倒数第2个id-- select left(ids, (CHAR_LENGTH(ids)-INSTR(reverse(ids),',') ) ) from (select GROUP_CONCAT(id ORDER BY created_time) ids, type, name, customer, `year_month`, count(1) c from test_table_02 GROUP BY type, name, customer, `year_month`having c > 1) aaaa) bbb) b on FIND_IN_SET(a.id, b.ids)
  • SUBSTR(ids,INSTR(ids,',')+1) 保留第一个 截取第2个到最后一个id
  • left(ids, (CHAR_LENGTH(ids)-INSTR(reverse(ids), ',') ) ) 保留最后一个 截取第1个到倒数第2个id
    • reverse(ids) 反转字符串
    • INSTR(reverse(ids), ',') 获取最后一个id的长度,包括了逗号的长度
    • CHAR_LENGTH(ids) 获取字符长度
    • CHAR_LENGTH(ids)-INSTR(reverse(ids), ',') 字符总长度 - 最后一个id+逗号的长度 = 第1个到倒数第2个id的长度

扩展

求长度时,注意length()、char_length()的区别
  • MySQL中length()、char_length()的区别和用法

  • char_length(str) 字符长度

    • 不管汉字还是数字或者是字母都算是一个字符
  • length(str) 计算单位:字节

    • utf8编码:一个汉字三个字节,一个数字或字母一个字节。
    • gbk编码:一个汉字两个字节,一个数字或字母一个字节。
  • 没有中文之类的,LENGTH和CHAR_LENGTH结果大概是一致的

    -- 6 计算字节select LENGTH('你好')-- 2 计算字符select CHAR_LENGTH('你好')
保留第一个:使用SUBSTR() 函数
set @ids = '12,3,4,5,6';-- MySQL SUBSTR() 函数从一个字符串中返回一个【从指定位置开始】的【指定长度】的子字符串。-- 可以传2个参数,也可以传3个,不传第3个参数len,指定长度,就是到结尾-- SUBSTR(str, pos)-- SUBSTR(str, pos, len)-- 从第2个id开始取到结尾 保留第一个select SUBSTR(@ids, INSTR(@ids,',') + 1) -- 3,4,5,6
保留最后一个:left() 函数
set @ids = '12,3,4,5,6';-- 从头取到倒数第二个 保留最后一个-- REVERSE() 函数返回反转后的字符串-- CHAR_LENGTH() 返回给定字符串的长度,注意与 LENGTH() 区别,LENGTH()函数返回指定字符串的以字节为单位的长度 -- UTF-8,一个中文字占用 3 个字节select left(@ids, (CHAR_LENGTH(@ids)-INSTR(reverse(@ids),','))) -- 12,3,4,5

来源地址:https://blog.csdn.net/weixin_44174211/article/details/129412634

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

mysql清理重复数据,并保留最新一条

下载Word文档到电脑,方便收藏和打印~

下载Word文档

猜你喜欢

mysql清理重复数据,并保留最新一条

背景 之前,数据是通过表单提交 后来增加了excel批量导入的功能,但是这个接口没有判断数据重复,覆盖更新 导致线上环境出现大量重复数据 如果要保证数据库不出现重复数据,可以添加唯一索引来限制 参考:Mysql重复数据查重保留一条(i
2023-08-16

Mysql 删除重复数据保留一条有效数据(最新推荐)

目录mysql 删除重复数据保留一条有效数据一、Mysql 删除重复数据,保留一条有效数据二、Mysql 删除重复数据(多个字段分组)三、Mysql 查询出可以删除的重复数据补充:mysql删除重复记录并且只保留一条MySql如何删除所有多
2023-02-06

oracle去除重复数据并保留一条

一般用第二种方法即可。
oracle去除重复数据并保留一条
2019-04-16

Mysql删除重复数据只保留一条

(1)以这张表为例: CREATE TABLE `test` ( `id` varchar(32) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '注解id',
2023-08-16

Mysql删除重复数据并且只保留一条(附实例!)

(1)以这张表为例:CREATE TABLE `test` (`id` varchar(32) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '注解id',`na
2023-02-01

MySQL怎样删除重复数据,只保留一条?

在实际工作开发过程中,常常会遇到数据库表中存在多条数据重复了,此时我们需要删除重复数据,只保留其中一条有效的数据; 针对这种场景,我们用SQL语句该怎么实现呢? 数据准备 建表语句: DROP TABLE IF EXISTS `test`;
2023-08-30

MySQL大量脏数据,如何只保留最新的一条?

因为系统的一个Bug,导致数据库表中出现重复数据,需要做的是删除重复数据且只保留最新的一条数据。具体场景是这样的有张订单关联额外费用表,而且一个订单号(order_no)记录只能关联同一个费用(cost_id)一次,但是数据库中出现了同
2023-04-21

MySQL大量脏数据如何只保留最新的一条(最新推荐)

这篇文章主要介绍了MySQL大量脏数据,如何只保留最新的一条,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
2023-05-16

MySQL 数据库查询数据,过滤重复数据保留一条数据-

转自: http://www.maomao365.com/?p=10564  摘要: 下文讲述MySQL数据库查询重复数据时,只保留一条数据的方法 实现思路: 在MySQL数据库中没有row_number函数,所以我们需变向实现此功能。 --1.基础数据
MySQL 数据库查询数据,过滤重复数据保留一条数据-
2021-10-02

mysql查询重复数据只保留一条怎么实现

要查询重复数据并保留一条唯一记录,可以使用以下步骤来实现:使用GROUP BY子句和聚合函数来找出重复数据,并只保留一条记录。使用HAVING子句来筛选出重复数据的记录。使用子查询或临时表来存储重复数据的记录,并通过主键或唯一索引来删除
mysql查询重复数据只保留一条怎么实现
2024-03-05

Oracle中实现删除重复数据只保留一条

目录oracle删除重复数据只保留一条Oracle删除重复记录,保留一条,没有主键的情况总结Oracle删除重复数据只保留一条查询及删除重复记录的SQL语句1、查找表中多余的重复记录,重复记录是根据单个字段(Id)来判断select
2023-02-15

mysql删除重复记录并且只保留一条的实现方法

准备的测试表结构及数据插入的数据中A,B,E存在重复数据,C没有重复记录CREATE TABLE `tab` (`id` int(11) NOT NULL AUTO_INCREMENT,`name` varchar(20) DEFAUL
2023-01-04

oracle/mysql数据库多条重复数据如何取最新的

目录mysql1、分组取最新的,再用最新的字段连表,回查数据①按分组字段取最新的,通过主键id回表查数据②非主键字段oracle1、原理讲解-可直接看22、在重复数据取最新的3、若要删除不满足条件附:ORACLE 查询某个时间之前的重复数据
oracle/mysql数据库多条重复数据如何取最新的
2024-08-09

MySQL中通过SQL语句删除重复记录并且只保留一条记录

目录一、单个字段的操作1、 查询全部重复的数据2、删除全部重复试题3、查询表中多余重复试题(根据depno来判断,除了rowid最小的一个)4、删除表中多余重复试题并且只留1条二、多个字段的操作总结最近在做题库系统,由于在题库中添加了重复的
2023-01-04

编程热搜

目录