[Redis][事务]详细讲解
目录
- 0.什么是事务?
- 1.Redis 事务本质
- 2.Redis 事务意义
- 3.事务操作
- 1.MULTI
- 2.EXEC
- 3.DISCARD
- 4.WATCH
- 5.UNWATCH
0.什么是事务?
- Redis的事务和MySQL的事务概念上是类似的,都是把一系列操作绑定成一组,让这一组能够批量执行
- Redis事务和MySQL的区别:
- 弱化的原子性:Redis没有”回滚机制”,只能做到这些操作”批量执行”,不能做到”一个失败就恢复到初始状态”
- 如果事务中若干个操作,存在有失败的,那就失败吧,不会有回滚操作
- 不保证一致性:不涉及”约束”,也没有回滚,事务执行过程中如果某个修改操作出现失败,就可能引起不一致的情况
- MySQL的一致性体现的是运行事务前后运行后,结果都是合理有效的,不会出现中间非法状态
- 不需要隔离性:也没有隔离级别,因为不会并发执行事务(Redis单线程处理请求)
- 不需要持久型:是保存在内存的,是否开启持久化,是
redis-server自己的事情,和事务无关
- 弱化的原子性:Redis没有”回滚机制”,只能做到这些操作”批量执行”,不能做到”一个失败就恢复到初始状态”
- Redis如果按照集群模式部署,就不支持事务
1.Redis 事务本质
- Redis事务**本质**上是在服务器上搞了一个”事务队列”,每次客户端在事务中进行一个操作,都会把命令先发给服务器,放到”事务队列”中(但是不会立即执行),而是会在真正收到
EXEC命令之后,才真正执行队列中的所有操作- 因此,Redis事务的功能相比于MySQL来说,是弱化很多的,只能保证事务中的这几个操作是”连续的”,不会被别的客户端”加塞”,仅此而已
- 综上:
- Redis事务的意义,就是为了"打包",避免其他客户端的命令,插队到中间
- 此处的不被插队,不是先抢占位置,而是先让出位置
2.Redis 事务意义
- Redis的事务为啥就搞的这么简单,为啥不设计成和MySQL一样强大呢?
- MySQL的事务,在背后付出了很大的代价
- 空间上,要花费更多的空间来存储更多的数据
- 时间上,也要有更大的开销
- 正是因为MySQL有上述的问题,才有了Redis的用武之地
- MySQL的事务,在背后付出了很大的代价
- 什么时候需要使用到Redis事务呢?
- 需要把多个操作打包进行,使用Redis事务比较合适
- 示例:商品抢购
- 典型写法如果不加上任何限制,就可能会出现线程安全问题
- 在多线程中,通过加锁的方式,来避免"插队"
if(count > 0) {// 下单成功count-- } - 在Redis中直接使用事务即可
# 开启事务 get count if count > 0decr count # 执行事务 # Redis服务器收到执行事务操作的时候,才会真正执行
- 典型写法如果不加上任何限制,就可能会出现线程安全问题
- 说明:
- Redis原生命令中不支持条件判定,但是Redis支持lua脚本,可以通过lua实现
- 可以认为lua脚本的实现方式是Redis事务的进阶版本
3.事务操作
1.MULTI
- 功能:开启一个事务,执行成功返回OK
- 当开启事务,并且向服务器发送若干个命令之后,此时服务器重启,此时的这个事务怎么办?
- 此时的效果相当于
DISCARD
- 此时的效果相当于
2.EXEC
- 功能:真正执行事务
- 每次添加一个操作,都会提示”
QUEUED”,说明命令已经进入服务端的队列了 - 真正执行
EXEC的时候,服务器才会真正执行命令
- 每次添加一个操作,都会提示”
- 示例:
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379> set k1 1
QUEUED
127.0.0.1:6379> set k2 2
QUEUED
127.0.0.1:6379> set k3 3
QUEUED
127.0.0.1:6379> EXEC
1) OK
2) OK
3) OK127.0.0.1:6379> get k1
"1"
127.0.0.1:6379> get k2
"2"
127.0.0.1:6379> get k3
"3
3.DISCARD
- 功能:放弃当前事务,此时直接清空事务队列,之前的操作都不会真正执行到
- 示例:
127.0.0.1:6379> MULTI OK 127.0.0.1:6379> set k1 1 QUEUED 127.0.0.1:6379> set k2 2 QUEUED 127.0.0.1:6379> DISCARD OK127.0.0.1:6379> get k1 (nil) 127.0.0.1:6379> get k2 (nil)
4.WATCH
- 情景:在执行事务的时候,如果某个事务中修改的值,被别的客户端修改了,此时就容易出现数据不一致的问题
- 此时
key的值是多少呢?- 从输入命令的时候看,是客户端1先执行的
set key 100,客户端2后执行的set key 200,但是从实际的执行时间看,是客户端2先执行的,客户端1后执行的# 客⼾端 1 先执⾏ 127.0.0.1:6379> MULTI OK 127.0.0.1:6379> set key 100 QUEUED# 客⼾端 2 再执⾏ 127.0.0.1:6379> set key 200 OK# 客⼾端 1 最后执⾏ 127.0.0.1:6379> EXEC 1) OK# 结果查询 127.0.0.1:6379> get key "100" - 这个时候,其实很容易引起歧义
- 因此,即使不保证严格的隔离性,至少也要告诉用户,当前的操作可能存在风险
- 从输入命令的时候看,是客户端1先执行的
watch命令就是用来解决这个问题的,watch在该客户端上监控一组具体的key- 当开启事务的时候,如果对
watch的key进行修改,就会记录当前key的”版本号” - 在真正提交事务的时候,如果发现当前服务器上的
key的版本号已经超过了事务开始时的版本号,就会让事务执行失败
- 当开启事务的时候,如果对
watch本质上是给exec加了个判定条件,属于"乐观锁"- 示例:
# 客户端1先执行 127.0.0.1:6379> watch k1 OK 127.0.0.1:6379> MULTI OK 127.0.0.1:6379> set k1 100 QUEUED 127.0.0.1:6379> set k2 1000 QUEUED # 只是入队列,但是不提交事务执行# 客户端2后执行 127.0.0.1:6379> set k1 200 OK# 客户端1再执行 127.0.0.1:6379> EXEC (nil) 127.0.0.1:6379> get k1 "200" 127.0.0.1:6379> get k2 (nil) # 此时说明事务已经被取消了,这次提交的所有命令都没有执行
5.UNWATCH
- 功能:取消对
key的监控,相当于WATCH的逆操作
相关文章:
[Redis][事务]详细讲解
目录 0.什么是事务?1.Redis 事务本质2.Redis 事务意义3.事务操作1.MULTI2.EXEC3.DISCARD4.WATCH5.UNWATCH 0.什么是事务? Redis的事务和MySQL的事务概念上是类似的,都是把一系列操作绑定成一组,让这一组能够批量执行Redis事务和M…...
Latex——一行的划线 如何分开
代码: \cmidrule(r){3-4} \cmidrule(r){5-6} \cmidrule(r){7-8}效果: 参考文章: LaTeX技巧653:如何隔开LaTeX表格邻近\cline表格线?...
大数据:快速入门Scala+Flink
一、什么是Scala Scala 是一种多范式编程语言,它结合了面向对象编程和函数式编程的特性。Scala 这个名字是“可扩展语言”(Scalable Language)的缩写,意味着它被设计为能够适应不同规模的项目,从小型脚本到大型分布式…...
侧边菜单的展开和折叠
环境准备:Vue3Element-UI Plus <script setup> import {ref} from "vue";// 是否折叠菜单,默认折叠 const isCollapse ref(true)</script><template><el-container><el-aside><el-menu:collapse"isCo…...
自动化办公-Python中的for循环
for 循环是 Python 中用于迭代(遍历)序列(如列表、元组、字典、集合、字符串)或其他可迭代对象的控制结构。它允许您逐一访问序列中的每个元素,并对其执行操作。以下是对 for 循环的详细介绍,包括语法、使用…...
Python_itertools
itertools itertools.count(start, step) 返回一个无限迭代器,从指定的start开始,每次增加step。 import itertools # 从1开始,每次增加1,输出前5个数 for i in itertools.count(1, 1):if i > 5:breakprint(i)运行结果&#…...
Apache Iceberg 数据类型参考表
Apache Iceberg 概述-链接 Apache Iceberg 数据类型参考表 数据类型描述实例方法注意事项BOOLEAN布尔类型,表示真或假true, false用于条件判断,例如 WHERE is_active true。确保逻辑条件的正确性。INTEGER32位有符号整数42, -7可用于计算、聚合…...
职责链模式
职责链模式 责任链(Chain of Responsibility)模式:为了避免请求发送者与多个请求处理者耦合在一起,于是将所有请求的处理者通过前一对象记住其下一个对象的引用而连成一条链;当有请求发生时,可将请求沿着这…...
新品 | Teledyne FLIR IIS 推出Forge 1GigE SWIR 短波红外工业相机系列
近日,51camera的合作伙伴Teledyne FLIR IIS推出了新品Forge 1GigE SWIR 130万像素的红外相机。 Forge 1GigE SWIR系列的首款相机配备宽频带、高灵敏度的Sony SenSWIR™️ 130万像素IMX990 InGaAs传感器。这款先进的传感器采用5um像素捕捉可见光和SWIR光谱ÿ…...
深入MySQL:掌握索引、事务、视图、存储过程与性能优化
在掌握了MySQL的基本操作之后,你可能会遇到更复杂的数据管理和优化需求。本文将介绍一些MySQL的进阶特性,包括索引、事务、视图、存储过程和函数、以及性能优化等内容。通过学习这些高级功能,你可以更高效地管理和优化你的数据库。 索引 索…...
【WSL——Windows 上使用 Linux 环境】
引入 以前在windows上使用linux工具链,一般都要安装虚拟机(VMware/virtualBox)。虚拟机的缺点是,因为是完整的虚拟环境,消耗系统资源比较多。 windows自己开发了WSL功能,实现了虚拟机的功能,但是比虚拟机性…...
Redis:事务
什么是Redis事务 Redis 事务的本质是一组命令的集合。事务支持一次执行多个命令,一个事务中所有命令都会被序列化。在事务执行过程,会按照顺序串行化执行队列中的命令,其他客户端提交的命令请求不会插入到事务执行命令序列中。 总结说&…...
策略模式的介绍和具体实现
❤ 作者主页:李奕赫揍小邰的博客 ❀ 个人介绍:大家好,我是李奕赫!( ̄▽ ̄)~* 🍊 记得点赞、收藏、评论⭐️⭐️⭐️ 📣 认真学习!!!🎉🎉 文章目录 策略接口三种…...
MySQL InnoDB MVCC数据结构分析
1、概述 MVCC(Multiversion Concurrency Control)多版本并发控制,通过维护不同的版本号,提供一种很好的并发控制技术,这种技术能够使读写操作不冲突,提升并发性能。 MySQL InnoDB存储引擎,在更…...
MySQL 8 查看 SQL 语句的执行进度
目录 1. 查询各阶段执行进度 (1)开启收集与统计汇总执行阶段信息的功能 (2)确定执行的SQL所属的thread_id (3)查询各阶段的执行进度 2. 查询SQL语句的整体执行进度 1. 查询各阶段执行进度 ࿰…...
OpenStack 部署实践与原理解析 - Ubuntu 22.04 部署 (DevStack)
提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 前言OpenStack 原理详解1. OpenStack 的架构2. OpenStack 的工作原理3. OpenStack 的 API4. 扩展性和模块化 OpenStack 安装方式比较1. DevStack2. Kolla3. OpenSta…...
【软件工程】可行性研究
一、目的 二、任务 三、步骤 四、结果:可行性研究报告 例题 选择题...
乌克兰因安全风险首次禁用Telegram
据BleepingComputer消息,乌克兰国家网络安全协调中心 (NCCC) 以国家安全为由,已下令限制在政府机构、军事单位和关键基础设施内使用 Telegram 消息应用程序。 这一消息通过NCCC的官方 Facebook 账号对外发布,在公告中乌…...
[SDX35]SDX35如何查看GPIO的Base值
SDX35 SDX35介绍 SDX35设备是一种多模调制解调器芯片,支持 4G/5G sub-6 技术。它是一个4nm芯片专为实现卓越的性能和能效而设计。它包括一个 1.9 GHz Cortex-A7 应用处理器。 SDX35主要特性 ■ 3GPP Rel. 17 with 5G Reduced Capability (RedCap) support. Backward compati…...
【Linux学习】【Ubuntu入门】2-1-1 vim编辑器设置
设置TAB键为4字节及显示行号 VIM编辑器默认TAB键为8空格,改为4空格 输入命令sudo vi /etc/vim/vimrc回车后输入密码按键盘下键到最后,按下“a”进入编辑模式,输入set ts4设置为4空格下一行输入set nu显示行号...
Springcloud:Eureka 高可用集群搭建实战(服务注册与发现的底层原理与避坑指南)
引言:为什么 Eureka 依然是存量系统的核心? 尽管 Nacos 等新注册中心崛起,但金融、电力等保守行业仍有大量系统运行在 Eureka 上。理解其高可用设计与自我保护机制,是保障分布式系统稳定的必修课。本文将手把手带你搭建生产级 Eur…...
C++使用 new 来创建动态数组
问题: 不能使用变量定义数组大小 原因: 这是因为数组在内存中是连续存储的,编译器需要在编译阶段就确定数组的大小,以便正确地分配内存空间。如果允许使用变量来定义数组的大小,那么编译器就无法在编译时确定数组的大…...
C# 表达式和运算符(求值顺序)
求值顺序 表达式可以由许多嵌套的子表达式构成。子表达式的求值顺序可以使表达式的最终值发生 变化。 例如,已知表达式3*52,依照子表达式的求值顺序,有两种可能的结果,如图9-3所示。 如果乘法先执行,结果是17。如果5…...
[大语言模型]在个人电脑上部署ollama 并进行管理,最后配置AI程序开发助手.
ollama官网: 下载 https://ollama.com/ 安装 查看可以使用的模型 https://ollama.com/search 例如 https://ollama.com/library/deepseek-r1/tags # deepseek-r1:7bollama pull deepseek-r1:7b改token数量为409622 16384 ollama命令说明 ollama serve #:…...
windows系统MySQL安装文档
概览:本文讨论了MySQL的安装、使用过程中涉及的解压、配置、初始化、注册服务、启动、修改密码、登录、退出以及卸载等相关内容,为学习者提供全面的操作指导。关键要点包括: 解压 :下载完成后解压压缩包,得到MySQL 8.…...
Python训练营-Day26-函数专题1:函数定义与参数
题目1:计算圆的面积 任务: 编写一个名为 calculate_circle_area 的函数,该函数接收圆的半径 radius 作为参数,并返回圆的面积。圆的面积 π * radius (可以使用 math.pi 作为 π 的值)要求:函数接收一个位置参数 radi…...
前端调试HTTP状态码
1xx(信息类状态码) 这类状态码表示临时响应,需要客户端继续处理请求。 100 Continue 服务器已收到请求的初始部分,客户端应继续发送剩余部分。 2xx(成功类状态码) 表示请求已成功被服务器接收、理解并处…...
【java面试】微服务篇
【java面试】微服务篇 一、总体框架二、Springcloud(一)Springcloud五大组件(二)服务注册和发现1、Eureka2、Nacos (三)负载均衡1、Ribbon负载均衡流程2、Ribbon负载均衡策略3、自定义负载均衡策略4、总结 …...
「Java基本语法」变量的使用
变量定义 变量是程序中存储数据的容器,用于保存可变的数据值。在Java中,变量必须先声明后使用,声明时需指定变量的数据类型和变量名。 语法 数据类型 变量名 [ 初始值]; 示例:声明与初始化 public class VariableDemo {publi…...
云原生时代的系统设计:架构转型的战略支点
📝个人主页🌹:一ge科研小菜鸡-CSDN博客 🌹🌹期待您的关注 🌹🌹 一、云原生的崛起:技术趋势与现实需求的交汇 随着企业业务的互联网化、全球化、智能化持续加深,传统的 I…...
