mysql 最后行加汇总_[mysql系列]6.幻读和间隙锁
幻读就是在同一个事务里面,前后两次查一个区间内的数据,看到了第一次查询看不到的行。
幻读会导致一个是锁语义上的问题,另外一个是数据不一致的问题。
语义上,我们看下面三个session的执行:
在time1时刻,先对d=5的所有行加行锁,然而time2的sessionb 还有time4的sessionC都没有依照sessionA的语义,所以time5的select产生了幻读的现象。
另外一个就是数据一致性的问题。在多个会话的情况下,会导致在binlog下的语句执行序列和预估的不一致,这样复制到备库也会出问题。因为语句只锁住行,所以没办法应对insert新的行进去,导致数据也不一致。
那么怎么解决幻读的问题呢?这里就要引进一个概念,间隙锁,锁住更改的行的间隙,这也是innodb的默认幻读现象解决方案,只在可重复读的事务隔离级别情况下。另外间隙锁之间并不会互斥,他表达的是一种保护作用,保护这个间隙,不被别的数据插入。
间隙锁和行锁合称为next-key lock,这种next-key lock解决了幻读的问题,但是也影响了并发程度,锁的粒度加大了。下面结合一些原则和案例分析一下:
先说下原则:1.加锁的基本单位是next-key lock,他是前开后闭区间
2.在select的时候,只有访问到的数据才会加锁
3.索引上等值查询,唯一索引加锁的时候,next-key 就是行锁。
4.索引上等值查询,向右方向遍历的时候,直到最后一个值不满足等值查询的时候才停下来,体现了间隙锁的特性。
我们先建立一个sql表和插入一些数据:
CREATE TABLE `t` ( `id` int(11) NOT NULL, `c` int(11) DEFAULT NULL, `d` int(11) DEFAULT NULL, PRIMARY KEY (`id`), KEY `c` (`c`)) ENGINE=InnoDB;insert into t values(0,0,0),(5,5,5),(10,10,10),(15,15,15),(20,20,20),(25,25,25);
基于这个表,结合上面的原则,举几个例子:
案例一 等值查询的间隙锁
为什么会出现sessionb和c的现象呢?结合上述提到的原则。根据间隙锁的左开右闭原则,sessionA的语句锁的是(5,10],另外这个是一个等职查询,最后一个值不满足不满足查询条件。所以最终锁(5,10),就出现了上叙现象。
案例二 覆盖索引加锁
share in mode因为覆盖索引的原因,只锁了c的那条B+树(根据上面的原则,只锁访问到的对象,id=5没有访问到,所有id的主键b+树没有锁,可以正常update)。但是如果是for update就粒度会包括id主键。
因为是普通索引,根据上面的原则,知道查到一个不满足等值的数才停下来,加间隙锁,锁住了(5,10)。所以sessionC被阻塞了。
案例三 主键索引的范围锁
先看下两个语义相同的sql语句
mysql> select * from t where id=10 for update;
mysql> select * from t where id>=10 and id<11 for update;
语义相同,但是锁的逻辑就不相同了,执行效果如图
按照惯例,依据前面的四大原则分析:id是唯一索引,next-key lock退化为行锁,所以对id=10的这一行加锁。然后范围查询,直到id=15这一行数据,停下来了。所以锁加在[10,15)。
而如果是非唯一索引,也执行相同的操作,比如:
那么将会全部被阻塞,因为将锁住(5,10]还有(10,15)因为他并不会退化成行锁,所以有两个间隙区间锁。
limit语句加锁
下面还是举一个例子,也是语义一致,但是加锁的粒度不同。
加了limit。虽然c=10的数据也不超过2条,逻辑上加不加没啥区别,但是锁的粒度就不一样了。
加了limit的语句,在找到第二条数据后就停止了新区间的加锁,但是如果没有limit会到下个数据不满足等值才停止加锁,那么c在(10,15)也是加锁状态,这条insert语句就会不成功,而limit,这条insert语句是成功的。
next key lock死锁
1.session A 启动事务后执行查询语句加 lock in share mode,在索引 c 上加了 next-key lock(5,10] 和间隙锁 (10,15),这个前面有例子。
2.session B 的 update 语句也要在索引 c 上加 next-key lock(5,10] ,进入锁等待
3.所以再insert进去就死锁了。这个时候innodb就会进行事务回滚。
mysql 最后行加汇总_[mysql系列]6.幻读和间隙锁相关推荐
- 使用mysql命令行的工具_[MySQL]命令行工具和基本操作
一 MySQL命令行工具 (查看帮助 ---help,或 -?) 1)MySQL MySQL是一个简单的SQL外壳(有GNUreadline功能).它支持交互式和非交互式使用.当交互使用时,查询结果 ...
- MySQL读已提交有间隙锁吗_mysql中的幻读与间隙锁
一.数据库隔离级别 一般来讲,数据库的隔离级别分为读未提交.读已提交(read commit,rc).可重复读(read reapeat,rr).串行化四个级别.在mysql中默认隔离级别是rr.读未 ...
- Mysql可重复读隔离级别下如何解决幻读
Mysql可重复读隔离级别下如何解决幻读 一些概念 具体加锁说明 使用主键索引进行等值查询 使用主键索引进行范围查询 使用二级索引进行等值查询 使用二级索引进行范围查询 一些概念 幻读:在一次事务中, ...
- MySQL 关键字和保留字汇总(MySQL 8.0)
MySQL 关键字和保留字汇总(MySQL 8.0) MySQL 关键字和保留字汇总(MySQL 8.0) MySQL 关键字和保留字汇总(MySQL 8.0) 关键字是在SQL中具有重要意义的单词, ...
- MySQL在RR级别下到底有没有修复幻读
微信搜索"coder-home"或扫一扫下面的二维码,关注公众号,第一时间了解更多干货分享,还有各类视频教程资源.扫描它,带走我 文章目录 背景 疑问点 分析 什么是快照读 开启事 ...
- MySQL可重复读隔离级别为何没有解决幻读(MVCC原理简介)
MySQL可重复读隔离级别为何没有解决幻读(MVCC原理简介) 一.MCVV简介 二.可重复读隔离级别能解决幻读? 三.什么是当前读和快照读? 四.MVCC的实现原理 五.RC,RR级别下的InnoD ...
- mysql pt工具 加索引_[转]MySQL中如何为连接添加索引
SELECT * FROM tblA, tblB, tblC WHERE tblA.col1 = tblB.col1 AND tblA.col2 = tblC.col1; explain的结果如下: ...
- mysql 单机双实列_{ mysql } MySQL单机多实例及主从复制
没有过多的,直接上码 my.cnf [mysql_multi] mysqld = /usr/bin/mysqld_safe mysqladmin = /usr/bin/mysqladmin user ...
- mysql 5 7 教程视频_[MySQL] MySQL 5.7从入门到精通视频教程
资源介绍 目录 ├─MySQL常用命令大全.pdf ├─视频教程 │xa0xa0├─第10讲 存储过程和函数 │xa0xa0│xa0xa0├─10.1xa0xa0创建存储过程和函数.avi │xa0x ...
- MySQL学习笔记:等值查询、范围查询、死锁、间隙锁的本质
环境 MySQL:5.7.26-log 前言 答疑文章(二):用动态的观点看加锁 原则 1:加锁的基本单位是 next-key lock.希望你还记得,next-key lock 是前开后闭区间. 原 ...
最新文章
- 链表 + 数组模拟链表
- 全国计算机等级二级证书foxbase,2002年4月全国计算机等级考试二级FOXBASE笔试试题...
- Andriod --- JetPack (二):LifeCycle 的诞生
- 上海库源电气OrCAD视频教程
- NSTimer注意内存泄露(真该死)
- 【牛客 - 302哈尔滨理工大学软件与微电子学院第八届程序设计竞赛同步赛(低年级)】 小乐乐算数字(水题,快速幂,lowbit)
- HandlerAdapter解析参数过程之HandlerMethodArgumentResolver
- 阿里云:Table Store(OTS) Writer
- Spring Boot使用自定义的properties
- python之函数用法__getitem__()
- 蓝桥杯1427: -买不到的数目(百钱百鸡问题变体)
- 碧桂园博智林机器人总部大楼_博智林机器人谷总部大楼完工
- Raki的读paper小记:Bipartite Flat-Graph Network for Nested Named Entity Recognition
- Linux服务器建立IP隧道,变更访问出口
- Go语言之高级篇beego框架之view
- 哈工大计算机网络第一章——计算机网络概述复习
- tensorflow机器学习之利用CNN卷积神经网络进行面部表情识别的实例代码
- 什么是淘宝店铺SKU
- 转载:【SQL练习】经典SQL练习题
- DIY时钟类--广州百田笔试之一
热门文章
- Atitit postgresql data type 数据类型与mysql对应表 数据库常用数据类型 	Postgre	Mysql	 整数	intgreter	Int	 小数	numeric	FL
- Atitit 命令行dsl传递参数的几种模式对比 cli url模式 键值对NameValuePair urlutil 	String string = -host 101.13
- Atitit 文档资料管理同步解决方案
- Atitit.在线充值功能的设计
- atitit.js 与c# java交互html5化的原理与总结.doc
- paip.提升用户体验---c++ QLabel标签以及QLineEdit文本框控件透明 设置
- 告诉你一个真实的数字化
- 金融用户画像的数据合规法律问题
- Rust : 为什么没有lifetime是不行的?
- 观点丨企业云管平台(CMP)项目成功的关键因素