Mysql中REPLACE INTO详解及和INSERT INTO的区别

前言

我们在进行数据库操作的时候,经常会遇到这样的场景:

  1. 首先判断数据是否存在;
  2. 如果不存在,则插入;
  3. 如果存在,则更新。

博主之前是是Java来进行逻辑判断,例如:

看起来似乎也很简洁,但是博主在一次偶然的机会接触到了REPLACE INTO。至此,这些 Java 代码全部可以省略!

接下来,我将带领大家一起学习REPLACE INTO这个强大的 SQL 语句。


官方地址:

MySQL :: MySQL 8.0 Reference Manual :: 15.2.12 REPLACE Statement

1. REPLACE INTO 原理

REPLACE INTOINSERT INTO功能类似,不同点在于:

  • 若表中的一条旧记录与一条使用PRIMARY KEY主键索引或使用UNIQUE 唯一索引的新记录具有相同的值,则先删除旧数据,再插入新数据。
  • 否则,直接插入新数据。`

尤其需要注意的是:

除非表有一个 PRIMARY KEYUNIQUE 索引,否则,使用一个 REPLACE INTO语句没有意义。它的功能将与 INSERT INTO一致,会直接插入数据,这将导致表中出现重复的数据!

了解了注意事项后,我们来归纳下REPLACE INTO的执行规则

  1. 当表没有主键和唯一键时,REPLACE INTO相当于普通的INSERT操作;binlog 记录事件为INSERT;返回的影响行数为INSERT的数量。
  2. 当表有主键没有唯一键时,REPLACE INTO插入记录与主键冲突时会进行DELETE+INSERT操作;binlog 记录事件为UPDATE;返回的影响行数为DELETE+INSERT的数量;如果主键自增,则AUTO_INCREMENT值不变。
  3. 当表有唯一键没有主键时,REPLACE INTO插入记录与唯一键冲突时会进行DELETE+INSERT操作;binlog 记录事件为UPDATE;返回的影响行数为DELETE+INSERT的数量。
  4. 当表同时存在主键和唯一键时,REPLACE INTO插入记录与主键冲突的时候进行DELETE+INSERT操作;binlog 记录事件为DELETE+INSERT;返回的影响行数为DELETE+INSERT的数量。如果主键自增,则AUTO_INCREMENT值不变。
  5. 当表同时存在主键和唯一键时,REPLACE INTO插入记录与唯一键冲突的时候进行DELETE+INSERT操作;binlog 记录事件为UPDATE;返回的影响行数为DELETE+INSERT的数量。如果主键自增,则新插入的这条记录的主键会变成最新 AUTO_INCREMENT 的值,而对应的 AUTO_INCREMENT 值会 +1。
  6. 当表同时存在主键和唯一键时,REPLACE INTO插入记录与一条记录主键和一条记录唯一键都冲突的时候进行DELETE+INSERT操作;binlog 记录事件为DELETE+UPDATE;返回的影响行数为DELETE*2+INSERT的数量。

总结

下面,我用表格来总结下使用 REPLACE INTO时可能会遇到的不同情况

  • 无主键无唯一索引

场景

REPLACE INTO 是相当于

REPLACE INTO 在 binlog 中的表现形式

返回的影响行数

无主键无唯一索引

INSERT

INSERT

INSERT 行数

  • 只有主键

场景

REPLACE INTO 是相当于

REPLACE INTO 在 binlog 中的表现形式

返回的影响行数

主键冲突

DELETE+INSERT

UPDTATE

DELETE+INSERT 行数

主键不冲突

INSERT

INSERT

INSERT 行数

  • 只有唯一索引

场景

REPLACE INTO 是相当于

REPLACE INTO 在 binlog 中的表现形式

返回的影响行数

唯一索引冲突

DELETE+INSERT

UPDTATE

DELETE+INSERT 行数

  • 有主键有唯一索引

场景

REPLACE INTO 是相当于

REPLACE INTO 在 binlog 中的表现形式

返回的影响行数

主键冲突唯一索引不冲突

DELETE+INSERT

DELETE+INSERT

DELETE+INSERT 行数

主键不冲突唯一索引冲突

DELETE+INSERT

UPDATE

DELETE+INSERT 行数

主键冲突唯一索引冲突

DELETE+INSERT

DELETE+INSERT

DELETE+INSERT 行数

主键不冲突唯一索引不冲突

INSERT

INSERT

INSERT 行数


2. REPLACE INTO 三种使用方式

value1,value2 均为模拟的表的属性名

REPLACE INTO 表名(value1, value2, ...) values(...);
REPLACE INTO 表名(value1, value2, ...) SELECT ....
REPLACE INTO 表名 SET value1 = value, ...

第一种形式与INSERT INTO的用法类似。

第二种形式相似于 INSERT SELECT。这种用法并不强制要求列名匹配,事实上,MYSQL 甚至不关心SELECT返回的列名,它需要的是列的位置。

eg:REPLACE INTO tb1( name, title, mood) SELECT rname, rtitle, rmood FROM tb2; 这个例子使用REPLACE INTO从 tb2 中将全部数据导入 tb1 中。

第三种形式相似于UPDATE SET用法。


3. REPALCE INTO 的坑

3.1. REPLACE INTO 与数据库设置自动更新时间的坑

REPLACE INTO在有主键或唯一索引冲突时,会执行DELETE+INSERT操作,若字段设置了自动更新,需要手动设置时间或者字段设置默认时间,否则时间字段会插入为空。

如下sql:

drop table if exists user_test;
create table user_test(
	id int primary key auto_increment comment '主键',
	name varchar(30)  not null comment '姓名',
	update_time timestamp on update CURRENT_TIMESTAMP comment '更新时间'
) comment '测试表';

insert into user_test(name,update_time) value ('zhangsan','2000-01-01 00:00:00');

此时执行 REPLACE INTO

replace into user_test(id,name) value (1,'zhangsan');

上图可以看出执行REPLACE INTO之后,update_time 的字段被更新为空了。

解决方案

# 方案一:建表时设置字段有默认时间
create table user_test(
	id int primary key auto_increment comment '主键',
	name varchar(30)  not null comment '姓名',
	update_time timestamp default current_timestamp on update CURRENT_TIMESTAMP comment '更新时间'
) comment '测试表';

# 方案二:replace into时手动设置时间
replace into user_test values(1,'zhangsan',now());

3.2. REPLACE INTO 匹配唯一索引更新时会导致主键自增值+1

当有主键有唯一索引且唯一索引冲突时并且主键设置成 AUTO_INCREMENT,那么使用REPLACE INTO会导致 AUTO_INCREMENT值自增 1。

3.3. REPLACE INTO 同事有主键和唯一索引冲突时可能会删除多条数据

使用replace into时只能用主键更新或者唯一键更新,二选其一。若同时都冲突了,可能会导致异常

4. 总结

REPLACE INTO存在暗坑。需谨慎使用。如果要实现上述说的需求可以使用另一种方式:on duplicate key update

当然,on duplicate key update为 Mysql 特有语法并且最好在单线程下操作。不然多线程下INSERT经常会导致锁表的情况发生,也是个小坑。在使用这些技术的时候,我们需要多加注意

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

基于Java Springboot发艺美发店管理系统

一、作品包含 源码数据库设计文档万字PPT全套环境和工具资源部署教程 二、项目技术 前端技术:Html、Css、Js、Vue、Element-ui 数据库:MySQL 后端技术:Java、Spring Boot、MyBatis 三、运行环境 开发工具:IDEA/eclipse 数据…

element ui 走马灯一页展示多个数据实现

element ui 走马灯一页展示多个数据实现 element ui 走马灯一页展示多个数据实现 element ui 走马灯一页展示多个数据实现 主要是对走马灯的数据的操作,先看js处理 let list [{ i: 1, name: 1 },{ i: 2, name: 2 },{ i: 3, name: 3 },{ i: 4, name: 4 },]let newL…

ACM招新赛<赛后题解与反思总结>③

问题 A: 数数(Easy) 题目描述 某一天,工作室需要统计人数,现在小劉开始数人数,但是由于小劉数学极差,因此他数数的时候总是会忘记数数字8,也就是说他数完7以后,就会直接数数字9,直观的讲就是数字…

网络安全:我们的安全防线

在数字化时代,网络安全已成为国家安全、经济发展和社会稳定的重要组成部分。网络安全不仅仅是技术问题,更是一个涉及政治、经济、文化、社会等多个层面的综合性问题。从宏观到微观,网络安全的重要性不言而喻。 宏观层面:国家安全与…

八、鸿蒙开发-网络请求、应用级状态管理

提示:本文根据b站尚硅谷2024最新鸿蒙开发HarmonyOS4.0鸿蒙NEXT星河版零基础教程课整理 链接指引 > 尚硅谷2024最新鸿蒙开发HarmonyOS4.0鸿蒙NEXT星河版零基础教程 文章目录 一、网络请求1.1 申请网络访问权限1.2 安装axios库1.2.1 配置环境变量1.2.2 第二步&…

【MySQL实战45讲笔记】基础篇——MySQL 的基础架构

目录 1. MySQL 的基础架构1.1 连接器1.2 查询缓存1.3 分析器1.4 优化器1.5 执行器 1. MySQL 的基础架构 我们由一个问题引入对MySQL 基础架构的学习:一条SQL查询语句是如何执行的? mysql> select * from T where ID10;通过分析学习MySQL…

计算机网络 (5)数据通信的基础知识

前言 数据通信是一种以信息处理技术和计算机技术为基础的通信方式,它通过数据通信系统将数据以某种信号方式从一处传送到另一处,为计算机网络的应用和发展提供了技术支持和可靠的通信环境,是现代通信技术的关键部分。 一、数据通信的基本概念…

【操作系统笔记】目录

【操作系统笔记】操作系统框架https://blog.csdn.net/Resurgence03/article/details/142624262 【操作系统笔记】CPU管理https://blog.csdn.net/Resurgence03/article/details/142621526 【操作系统笔记】内存管理https://blog.csdn.net/Resurgence03/article/details/142669…

linux之调度管理(7)-SMP cpu 的spin-table启动

一、smp启动总体介绍 soc在启动阶段除了一些特殊情况外(如为了加快启动速度,在bl2阶段通过并行加载方式同时加载bl31、bl32和bl33镜像),一般都没有并行化需求。因此只需要一个cpu执行启动流程即可,这个cpu被称为primar…

基于Java Springboot活力健身馆管理系统

一、作品包含 源码数据库设计文档万字PPT全套环境和工具资源部署教程 二、项目技术 前端技术:Html、Css、Js、Vue、Element-ui 数据库:MySQL 后端技术:Java、Spring Boot、MyBatis 三、运行环境 开发工具:IDEA/eclipse 数据…

BERT-TFBS:一种基于 BERT 的新型模型,通过迁移学习预测转录因子结合位点

转录因子(TF)是通过结合 DNA 序列中的转录因子结合位点(TFBS)来调控基因转录所必需的蛋白质。准确预测 TFBS 有助于设计和构建基于 TF 的代谢调控系统。尽管已经开发了各种用于预测 TFBS 的深度学习算法,但预测性能仍有…

前端pdf预览方案

前端pdf预览方案 pdf预览一般不需要前端生成pdf文件,pdf文件一般是通过接口,获取pdf文件【responseType:‘blob’,】或二进制文件流【responseType: ‘arraybuffer’,】或者已有的pdf文件。 前端PDF预览通常是通过读取现有的PDF文件,并使用…

得物彩虹桥架构演进之路-负载均衡篇

文 / 新一 一、前言 一年一更的彩虹桥系列又来了,在前面两期我们分享了在稳定性和性能2个层面的一些演进&优化思路。近期我们针对彩虹桥 Proxy 负载均衡层面的架构做了一次升级,目前新架构已经部署完成,生产环境正在逐步升级中&#xf…

Python3.11.9+selenium,获取图片验证码以及输入验证码数字

Python3.11.9+selenium,获取图片验证码以及输入验证码数字 1、遇到问题:登录或修改密码需要验证码 2、解决办法: 2.1、安装ddddocr pip install ddddocr 2.2、解析验证码函数 import ddddocr def get_capcha_text():#获取验证码图片ele_pic = driver.find_element(By.XPAT…

23种设计模式-状态(State)设计模式

文章目录 一.什么是状态模式?二.状态模式的结构三.状态模式的应用场景四.状态模式的优缺点五.状态模式的C实现六.状态模式的JAVA实现七.代码解释八.总结 类图: 状态设计模式类图 一.什么是状态模式? 状态模式(State Pattern&…

Chroma致茂Chroma61815回收式电网模拟电源

Chroma致茂 Chroma61815回收式电网模拟电源 产品特色 功率规格: 61809:9kVA 61812:12kVA 61815:15kVA 电压规格:0~350V 频率规格:30Hz~100Hz/DC 3U高度具备最大15kVA之高功率密度设计 全触控面板搭配直观的…

基于STM32的智能语音识别饮水机系统设计

功能描述 1、给饮水机设定称呼,喊出称呼,饮水机回答:我在 2、语音进行加热功能,说:请加热,加热片运行 3、饮水机水位检测,低于阈值播报“水量少,请换水” 4、检测饮水机水温&#xf…

Hadoop 学习心得

一、引言 (一)学习 Hadoop 的背景和目的 随着信息技术的飞速发展,数据量呈爆炸式增长,传统的数据处理方式已难以满足需求。在这样的背景下,为了能够在大数据领域有所发展,我开始学习 Hadoop。Hadoop 作为处…

使用Mybatis向Mysql中的插入Point类型的数据全方位解析

1. 结果 希望每一个能够看到结果的人都能自己装载进去!加油! 2.代码 2.1TestMapper import org.apache.ibatis.annotations.*; import java.util.Date; import java.util.List;/*** author Administrator*/ Mapper public interface TestMapper {/*…

阿里云轻量应用服务器可以用在哪些场景呢

在数字化转型的浪潮中,中小企业面临着如何快速、高效地上云的挑战。阿里云轻量应用服务器(SWAS)作为一款专为中小企业设计的云服务产品,提供了简单易用、经济实惠的解决方案,助力企业轻松实现云端部署,赋能…