当前位置:首页 > 科技  > 软件

select...for update,表锁?行锁?间隙锁?

来源: 责编: 时间:2023-11-06 08:52:26 173观看
导读大家好呀,我是楼仔。对于这个问题,我 4 年前就专门研究过,最近看到网上很多相关的文章,要么总结得不全,要么存在很多问题。感觉有必要自己写一篇,一方面对网上的知识进行纠偏,另一方面也想全面总结一下这块知识,方便大家学习

大家好呀,我是楼仔。mvT28资讯网——每日最新资讯28at.com

对于这个问题,我 4 年前就专门研究过,最近看到网上很多相关的文章,要么总结得不全,要么存在很多问题。mvT28资讯网——每日最新资讯28at.com

感觉有必要自己写一篇,一方面对网上的知识进行纠偏,另一方面也想全面总结一下这块知识,方便大家学习。mvT28资讯网——每日最新资讯28at.com

这篇文章应该是全网总结最全的,如果有发现比我这篇写得更好,更全,一定要私我哈。mvT28资讯网——每日最新资讯28at.com

不 BB,上文章目录:mvT28资讯网——每日最新资讯28at.com

图片图片mvT28资讯网——每日最新资讯28at.com

01 环境准备

在验证之前,我们先准备好具体的环境和数据,事务隔离级别 RR,数据库版本 5.7.26。mvT28资讯网——每日最新资讯28at.com

为了方便测试,索引都是整型:mvT28资讯网——每日最新资讯28at.com

CREATE TABLE user (  id int(11) unsigned NOT NULL AUTO_INCREMENT,  user_no int(11) NOT NULL COMMENT '用户编号',  user_name varchar(16) DEFAULT NULL COMMENT '用户名',  age int(3) DEFAULT NULL COMMENT '年龄',  PRIMARY KEY (id),  UNIQUE KEY un_idx_user_no (user_no),  KEY idx_age (age)) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8;

初始化数据:mvT28资讯网——每日最新资讯28at.com

insert into user values(1, 10, '楼仔', 18);insert into user values(4, 15, '二哥', 28);insert into user values(8, 20, '一灰', 38);

常用命令操作:mvT28资讯网——每日最新资讯28at.com

> start transaction; // 开启事务> commit; // 提交事务> rollback; // 回滚事务> select @@transaction_isolation; // 查看事务隔离级别> select @@version; // 查看数据库版本> SELECT * FROM INFORMATION_SCHEMA.INNODB_LOCKS; //  查询锁

02 场景分类

2.1 主键(有值)

说明:主键查询,查询数据存在。mvT28资讯网——每日最新资讯28at.com

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where id = 1 for update;

执行更新操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

update user set user_name = "楼仔小弟" where id = 1;ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

查看锁信息:mvT28资讯网——每日最新资讯28at.com

图片图片mvT28资讯网——每日最新资讯28at.com

  • lock_mode 为 X(排他锁)
  • lock_type 为 RECORD,行级锁

结论:查询条件为主键,且有值,行锁mvT28资讯网——每日最新资讯28at.com

2.2 主键(空值)

操作:主键查询,查询数据不存在。mvT28资讯网——每日最新资讯28at.com

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where id = 2 for update;

执行插入操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

insert into user values(3, 14, '楼仔小弟', 28);ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

这里的间隙锁,锁住的区间是 id 字段的 (1,4) 区间,查看锁信息:mvT28资讯网——每日最新资讯28at.com

图片图片mvT28资讯网——每日最新资讯28at.com

  • lock_mode 为 X(排他锁)+ Gap(间隙锁)
  • lock_type 为 RECORD,行级锁

结论:查询条件为主键,且空值,间隙锁mvT28资讯网——每日最新资讯28at.com

2.3 唯一索引(有值)

说明:唯一索引查询,数据存在。mvT28资讯网——每日最新资讯28at.com

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where user_no = 10 for update;

执行更新操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

update user set user_name = "楼仔小弟" where user_no = 10;ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

图片图片mvT28资讯网——每日最新资讯28at.com

结论:查询条件为唯一索引,且有值,行锁mvT28资讯网——每日最新资讯28at.com

2.4 唯一索引(空值)

说明:唯一索引查询,数据不存在。mvT28资讯网——每日最新资讯28at.com

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where user_no = 11 for update;

执行插入操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

insert into user values(3, 14, '楼仔小弟', 28);ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

这里的间隙锁,锁住的区间是 user_no 字段的 (1,4) 区间。mvT28资讯网——每日最新资讯28at.com

图片图片mvT28资讯网——每日最新资讯28at.com

结论:查询条件为唯一索引,且空值,间隙锁mvT28资讯网——每日最新资讯28at.com

2.5 普通索引(有值)

说明:普通索引,数据存在。mvT28资讯网——每日最新资讯28at.com

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where age = 18 for update;

执行更新操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

update user set user_name = "楼仔小弟" where age = 18;ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

图片图片mvT28资讯网——每日最新资讯28at.com

执行插入操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

insert into user values(3, 14, '楼仔小弟', 20);ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

图片图片mvT28资讯网——每日最新资讯28at.com

这里锁住的是 age 字段的 [18, 28) 这区间。mvT28资讯网——每日最新资讯28at.com

结论:查询条件为普通索引,且有值,间隙锁mvT28资讯网——每日最新资讯28at.com

2.6 普通索引(空值)

说明:普通索引,数据不存在。mvT28资讯网——每日最新资讯28at.com

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where age = 19 for update;

执行插入操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

insert into user values(3, 14, '楼仔小弟', 20);ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

图片图片mvT28资讯网——每日最新资讯28at.com

这里锁住的是 age 字段的 (18, 28) 这区间。mvT28资讯网——每日最新资讯28at.com

结论:查询条件为普通索引,且空值,间隙锁mvT28资讯网——每日最新资讯28at.com

2.7 索引(范围查询)

说明:这里的索引,包括主键索引、唯一索引和普通索引。mvT28资讯网——每日最新资讯28at.com

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where id > 1 for update;

执行插入操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

insert into user values(3, 14, '楼仔小弟', 20);ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

图片图片mvT28资讯网——每日最新资讯28at.com

这里其实可以对 id = 1 的数据进行更新,对于其它数据,都被锁住,锁住的范围是 id 字段的 (1, 4],(4, 8],(8, 正无穷) 区间。mvT28资讯网——每日最新资讯28at.com

结论:查询条件为索引,且是范围查询,间隙锁。mvT28资讯网——每日最新资讯28at.com

2.8 无索引

执行悲观锁查询:mvT28资讯网——每日最新资讯28at.com

select * from user where user_name = "楼仔" for update;

执行插入操作,被锁住了:mvT28资讯网——每日最新资讯28at.com

insert into user values(3, 14, '楼仔小弟', 20);ERROR 1205 (HY000): Lock wait timeout exceeded; try restarting transaction

图片mvT28资讯网——每日最新资讯28at.com

这里明显是锁表了,但是为什么锁的信息还是行锁呢,知道的同学,可以私我哈~~mvT28资讯网——每日最新资讯28at.com

结论:查询条件为无索引,表锁。mvT28资讯网——每日最新资讯28at.com

03 加锁规则

3.1 规律总结

我们把上面的结论进行汇总:mvT28资讯网——每日最新资讯28at.com

图片图片mvT28资讯网——每日最新资讯28at.com

总结如下规律:mvT28资讯网——每日最新资讯28at.com

  1. 当查询条件为主键和唯一索引,当有值时,是行锁;
  2. 当查询条件为主键和唯一索引,当为空值时,是间隙锁;
  3. 当查询条件为普通索引,是间隙锁;
  4. 当查询条件为索引,且为范围查询,是间隙锁;
  5. 当查询条件无索引,是表锁。

3.2 加锁规则

那是否有一套加锁规则呢?mvT28资讯网——每日最新资讯28at.com

为了便于大家理解,我先普及 3 个概念:mvT28资讯网——每日最新资讯28at.com

  • Record Lock:行锁
  • Gap Lock:间隙锁,锁定一个范围,但不包含记录本身
  • Next-Key Lock:行锁 + 间隙锁,左开右闭,比如(1,5]

其实 MySQL 大佬林晓斌在极客时间讲过,后来也有很多博主转发过他的加锁规则,我直接把这套规则贴一下。mvT28资讯网——每日最新资讯28at.com

两个“原则”:mvT28资讯网——每日最新资讯28at.com

  • 原则 1:加锁的基本单位是 next-key lock,其中 next-key lock 是前开后闭区间;
  • 原则 2:查找过程中访问到的对象才会加锁。

两个“优化”:mvT28资讯网——每日最新资讯28at.com

  • 优化 1:索引上的等值查询,给唯一索引加锁的时候,next-key lock退化为行锁;
  • 优化 2:索引上的等值查询,向右遍历时且最后一个值不满足等值条件的时候,next-key lock 退化为间隙锁。

3.3 分析一下

这里我们结合上面的案例,来解读这套加锁规则。mvT28资讯网——每日最新资讯28at.com

针对我们前面总结的 5 条规律,我们先分析这两条:mvT28资讯网——每日最新资讯28at.com

  • 当查询条件为主键和唯一索引,当有值时,是行锁;
  • 当查询条件为主键和唯一索引,当为空值时,是间隙锁。

下面我们根据 “两个原则” + “两个优化” 来分析一下。mvT28资讯网——每日最新资讯28at.com

根据 “原则 1”,加锁的基本单位是 next-key lock,当 “索引上为等值查询” 时(即能查到该数据),根据 “优化 1”,间隙锁退化为行锁。mvT28资讯网——每日最新资讯28at.com

同理,根据 “优化 2”,索引上的等值查询,向右遍历时且最后一个值不满足等值条件的时候,next-key lock 退化为间隙锁。mvT28资讯网——每日最新资讯28at.com

再分析这两条:mvT28资讯网——每日最新资讯28at.com

  • 当查询条件为普通索引,是间隙锁;
  • 当查询条件为索引,且为范围查询,是间隙锁;

同上,通过 “原则 1” 和 “优化 2”,普通索引 是加的间隙锁。mvT28资讯网——每日最新资讯28at.com

对于范围查询,个人认为上面的规则还不能完全覆盖,当时林晓斌针对这些规则,举了 4 个示例,然后进行详细剖析,包括间隙锁的范围区间计算。mvT28资讯网——每日最新资讯28at.com

因为篇幅原因,这里就不再详细展开,如果后续需要,我也可能会单独出一篇。mvT28资讯网——每日最新资讯28at.com

04 写在最后

最后我们再回顾一下(RR 隔离级别):mvT28资讯网——每日最新资讯28at.com

  1. 当查询条件为主键和唯一索引,当有值时,是行锁;
  2. 当查询条件为主键和唯一索引,当为空值时,是间隙锁;
  3. 当查询条件为普通索引,是间隙锁;
  4. 当查询条件为索引,且为范围查询,是间隙锁;
  5. 当查询条件无索引,是表锁。

至于间隙锁的范围,如何计算,本文没有详细阐述,但是上面的这些规则,就能基本满足我们日常工作需要。mvT28资讯网——每日最新资讯28at.com

本文链接:http://www.28at.com/showinfo-26-17150-0.htmlselect...for update,表锁?行锁?间隙锁?

声明:本网页内容旨在传播知识,若有侵权等问题请及时与本网联系,我们将在第一时间删除处理。邮件:2376512515@qq.com

上一篇: 2023年WebAssembly 现状

下一篇: 高性能Python开发:解密FastAPI的高并发秘籍!

标签:
  • 热门焦点
  • Mate60手机壳曝光 致敬自己的经典设计

    Mate60手机壳曝光 致敬自己的经典设计

    8月3日消息,今天下午博主数码闲聊站带来了华为Mate60的第三方手机壳图,可以让我们在真机发布之前看看这款华为全新旗舰的大致轮廓。从曝光的图片看,Mate 60背后摄像头面积依然
  • 天猫精灵Sound Pro体验:智能音箱没有音质?来听听我的

    天猫精灵Sound Pro体验:智能音箱没有音质?来听听我的

    这几年除了手机作为智能生活终端最主要的核心之外,第二个可以成为中心点的产品是什么?——是智能音箱。 手机在执行命令的时候有两种操作方式,手和智能语音助手,而智能音箱只
  • 印度登月最关键一步!月船三号今晚进入环月轨道

    印度登月最关键一步!月船三号今晚进入环月轨道

    8月5日消息,据印度官方消息,月船三号将于北京时间今晚21时30分左右开始近月制动进入环月轨道。这是该探测器能够成功的最关键步骤之一,如果成功将开始围
  • 2023 年的 Node.js 生态系统

    2023 年的 Node.js 生态系统

    随着技术的不断演进和创新,Node.js 在 2023 年达到了一个新的高度。Node.js 拥有一个庞大的生态系统,可以帮助开发人员更快地实现复杂的应用。本文就来看看 Node.js 最新的生
  • 猿辅导与新东方的两种“归途”

    猿辅导与新东方的两种“归途”

    作者|卓心月 出品|零态LT(ID:LingTai_LT)如何成为一家伟大企业?答案一定是对“势”的把握,这其中最关键的当属对企业战略的制定,且能够站在未来看现在,即使这其中的
  • 2纳米决战2025

    2纳米决战2025

    集微网报道 从三强争霸到四雄逐鹿,2nm的厮杀声已然隐约传来。无论是老牌劲旅台积电、三星,还是誓言重回先进制程领先地位的英特尔,甚至初成立不久的新
  • OPPO K11评测:旗舰级IMX890加持 2000元档最强影像手机

    OPPO K11评测:旗舰级IMX890加持 2000元档最强影像手机

    【Techweb评测】中端机型用户群体巨大,占了中国目前手机市场的大头,一直以来都是各手机品牌的“必争之地”,其中OPPO K系列机型一直以来都以高品质、
  • 朋友圈可以修改可见范围了 苹果用户可率先体验

    朋友圈可以修改可见范围了 苹果用户可率先体验

    近日,iOS用户迎来微信8.0.27正式版更新,除了可更换二维码背景外,还新增了多项实用功能。在新版微信中,朋友圈终于可以修改可见范围,简单来说就是已发布的朋友圈
  • 亲历马斯克血洗Twitter,硅谷的苦日子在后头

    亲历马斯克血洗Twitter,硅谷的苦日子在后头

    文/刘哲铭  编辑/李薇  马斯克再次挥下裁员大刀。  美国时间11月14日,Twitter约4400名外包员工遭解雇,此次被解雇的员工的主要工作为内容审核等。此前,T
Top