iis服务器助手广告
返回顶部
首页 > 资讯 > 数据库 >Mysql七种锁
  • 626
分享到

Mysql七种锁

mysqljavaPoweredby金山文档 2023-09-05 11:09:14 626人浏览 安东尼
摘要

Mysql是目前世界上最流行的数据库,InnoDB是mysql最流行的存储引擎,它在大数据量高并发量的业务场景下,有着非常良好的性能表现,之所以如此,是和InnoDB的锁机制相关。 总的来说,InnoDB共有七种类型的锁: (1)自增锁

Mysql是目前世界上最流行的数据库,InnoDB是mysql最流行的存储引擎,它在大数据高并发量的业务场景下,有着非常良好的性能表现,之所以如此,是和InnoDB的机制相关。

总的来说,InnoDB共有七种类型的锁:

(1)自增锁(Auto-inc Locks);

(2)共享/排它锁(Shared and Exclusive Locks);

(3)意向锁(Intention Locks);

(4)插入意向锁(Insert Intention Locks);

(5)记录锁(Record Locks);

(6)间隙锁(Gap Locks);

(7)临键锁(Next-key Locks);

第一种,自增锁(Auto-inc Locks)

【案例说明】

Mysql,InnoDB,默认的隔离级别(RR),假设有数据表:

t(id AUTO_INCREMENT, name);

数据表中有数据:

1, wangwu

2, zhangsan

3, lisi

事务A先执行,还未提交:

insert into t(name) values(xxx);

事务B后执行:

insert into t(name) values(ooo);

问:事务B会不会被阻塞?

【案例分析】

InnoDB在RR隔离级别下,尝试解决幻读问题,上面这个案例中:

(1)事务A先执行insert,会得到一条(4, xxx)的记录,由于是自增列,故不用显示指定id为4,InnoDB会自动增长,注意此时事务并未提交;

(2)事务B后执行insert,假设不会被阻塞,那会得到一条(5, ooo)的记录;

此时,并未有什么不妥,但如果,

(3)事务A继续insert:

insert into t(name) values(xxoo);

会得到一条(6, xxoo)的记录。

(4)事务A再select:

select * from t where id>3;

得到的结果是:

4, xxx

6, xxoo

画外音:不可能查询到5的记录,在RR的隔离级别下,不可能读取到还未提交事务生成的数据。

这对于事务A来说,就很奇怪了,AUTO_INCREMENT的列,连续插入了两条记录,一条是4,接下来一条变成了6,就像莫名其妙的幻影。

【自增锁】

自增锁是一种特殊的表级别锁(table-level lock),专门针对事务插入AUTO_INCREMENT类型的列。

最简单的情况,如果一个事务正在往表中插入记录,所有其他事务的插入必须等待,以便第一个事务插入的行,是连续的主键值。

与此同时,InnoDB提供了innodb_autoinc_lock_mode配置,可以调节与改变该锁的模式与行为。

第二种,共享/排它锁(Shared and Exclusive Locks)

(1)事务拿到某一行记录的共享S锁,才可以读取这一行;

(2)事务拿到某一行记录的排它X锁,才可以修改或者删除这一行;

其兼容互斥表如下:

即:

(1)多个事务可以拿到一把S锁,读读可以并行;

(2)而只有一个事务可以拿到X锁,写写/读写必须互斥;

共享/排它锁的潜在问题是,不能充分的并行,解决思路是数据多版本

第三种,意向锁(Intention Locks)

InnoDB支持多粒度锁(multiple granularity locking),它允许行级锁与表级锁共存,实际应用中,InnoDB使用的是意向锁。

意向锁是指,未来的某个时刻,事务可能要加共享/排它锁了,先提前声明一个意向。

意向排它锁(intention exclusive lock, IX),它预示着,事务有意向对表中的某些行加排它X锁

select * from demo where id = 1 for update

上述语句执行的时候会对demo这张表添加一个表级别的意向排它锁,并且在id=1的记录上加一个行级别排它锁。

意向共享锁(intention shared lock, IS),它预示着,事务有意向对表中的某些行加共享S锁

select * from demo where id = 1

上述语句执行的时候会对demo这张表添加一个表级别的意向共享锁,并且在id=1的记录上加一个行级别共享锁。

第四种,插入意向锁(Insert Intention Locks)

对已有数据行的修改与删除,必须加强互斥锁X锁,那对于数据的插入,是否还需要加这么强的锁,来实施互斥呢?插入意向锁,孕育而生。

插入意向锁,是间隙锁(Gap Locks)的一种(所以,也是实施在索引上的),它是专门针对insert操作的。

1、插入意向锁是Gap锁,不是意向锁,是insert操作产生的。当多个事务同时将不同的数据写入同一个索引间隙时,不需要等待其他事务完成,也不会发生锁等待。

假定有一个记录索引包含键值4和7,不同的事务分别插入5和6,每个事务都会产生一个插入意向锁,加到4-7之间,得到插入行上的排他锁,但不会相互锁定,因为数据行并不冲突。

2. 插入意向锁不会阻止任何锁,插入记录会持有记录锁。

insert into test_user(user_id,name,age) values(2,'b',10)------- TRX HAS BEEN WaiTING 18 SEC FOR THIS LOCK TO BE GRANTED:RECORD LOCKS space id 6628 page no 4 n bits 72 index `index_user` of table `test`.`test_user` trx id 117851203插入意向锁 lock_mode X insert intention waitingRecord lock, heap no 1 PHYSICAL RECORD: n_fields 1; compact fORMat; info bits 0 0: len 8; hex 73757072656d756d; asc supremum;;

以上就是mysql插入意向锁的使用

第五种,记录锁(Record Locks)

记录锁,它封锁索引记录,例如:

select * from t where id=1 for update;

它会在id=1的索引记录上加锁,以阻止其他事务插入,更新,删除id=1的这一行。

需要说明的是:

select * from t where id=1;

是快照读(SnapShot Read),它并不加锁

第六种,间隙锁(Gap Locks)

建表和初始化语句如下:

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);

这个表除了主键id外,还有一个索引c

为了解决幻读问题,InnoDB引入了间隙锁,锁的就是两个值之间的空隙

当执行select * from t where d=5 for update的时候,就不止是给数据库中已有的6个记录加上了行锁,还同时加了7个间隙锁。这样就确保了无法再插入新的记录

行锁分成读锁和写锁

跟间隙锁存在冲突关系的是往这个间隙中插入一个记录这个操作。间隙锁之间不存在冲突关系

这里sessionB并不会被堵住。因为表t里面并没有c=7会这个记录,因此sessionA加的是间隙锁(5,10)。而sessionB也是在这个间隙加的间隙锁。它们用共同的目标,保护这个间隙,不允许插入值。但它们之间是不冲突的

间隙锁和行锁合称next-key lock,每个next-key lock是前开后闭区间。表t初始化以后,如果用select * from t for update要把整个表所有记录锁起来,就形成了7个next-key lock,分别是(-∞,0]、(0,5]、(5,10]、(10,15]、(15,20]、(20, 25]、(25, +supremum]。因为+∞是开区间,在实现上,InnoDB给每个索引加了一个不存在的最大值supremum,这样才符合都是前开后闭区间

间隙锁和next-key lock的引入,解决了幻读的问题,但同时也带来了一些困扰

间隙锁导致的死锁:

1.sessionA执行select … for update语句,由于id=9这一行并不存在,因此会加上间隙锁(5,10)

2.sessionB执行select … for update语句,同样会加上间隙锁(5,10),间隙锁之间不会冲突

3.sessionB试图插入一行(9,9,9),被sessionA的间隙锁挡住了,只好进入等待

4.sessionA试图插入一行(9,9,9),被sessionB的间隙锁挡住了

两个session进入互相等待状态,形成了死锁

间隙锁的引入可能会导致同样的语句锁住更大的范围,这其实是影响并发度的

在读提交隔离级别下,不存在间隙锁

第七种,临键锁(Next-Key Locks)

临键锁,是记录锁与间隙锁的组合,它的封锁范围,既包含索引记录,又包含索引区间。

更具体的,临键锁会封锁索引记录本身,以及索引记录之前的区间。

如果一个会话占有了索引记录R的共享/排他锁,其他会话不能立刻在R之前的区间插入新的索引记录。

t(id PK, name KEY, sex, flag);

表中有四条记录:

1, songliu, m, A

3, zhangsan, m, A

5, lisi, m, A

9, wangwu, f, B

PK上潜在的临键锁为:

(-infinity, 1]

(1, 3]

(3, 5]

(5, 9]

(9, +infinity)

临键锁的主要目的,也是为了避免幻读(Phantom Read)。如果把事务的隔离级别降级为RC,临键锁则也会失效。

总结

(1)自增锁(Auto-inc Locks):表级锁,专门针对事务插入AUTO_INC的列,如果插入位置冲突,多个事务会阻塞,以保证数据一致性;

(2)共享/排它锁(Shared and Exclusive Locks):行级锁,S锁与X锁,强锁;

(3)意向锁(Intention Locks):表级锁,IS锁与IX锁,弱锁,仅仅表明意向;

(4)插入意向锁(Insert Intention Locks):针对insert的,如果插入位置不冲突,多个事务不会阻塞,以提高插入并发;

(5)记录锁(Record Locks):索引记录上加锁,对索引记录实施互斥,以保证数据一致性;

(6)间隙锁(Gap Locks):封锁索引记录中间的间隔,在RR下有效,防止间隔中被其他事务插入;

(7)临键锁(Next-key Locks):封锁索引记录,以及索引记录中间的间隔,在RR下有效,防止幻读;

来源地址:https://blog.csdn.net/songmulin/article/details/128650209

您可能感兴趣的文档:

--结束END--

本文标题: Mysql七种锁

本文链接: https://www.lsjlt.com/news/395173.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

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

下载Word文档
猜你喜欢
  • Mysql七种锁
    MySQL是目前世界上最流行的数据库,InnoDB是MySQL最流行的存储引擎,它在大数据量高并发量的业务场景下,有着非常良好的性能表现,之所以如此,是和InnoDB的锁机制相关。 总的来说,InnoDB共有七种类型的锁: (1)自增锁...
    99+
    2023-09-05
    mysql java Powered by 金山文档
  • MySQL七种JOIN类型小结
            在开始之前,我们创建两个表用于演示将要介绍的其中JOIN类型。 建表 CREATE...
    99+
    2024-04-02
  • mysql锁之三种行级锁介绍
    本文主要介绍 1.mysql三种行锁介绍 2.RR模式下,next-key lock为什么可以解决幻读问题 首先,创建一张表: mysql> show create table test0...
    99+
    2024-04-02
  • MySQL中七种JOIN的SQL是怎样的
    这篇文章将为大家详细讲解有关MySQL中七种JOIN的SQL是怎样的,文章内容质量较高,因此小编分享给大家做个参考,希望大家阅读完这篇文章后对相关知识有一定的了解。准备数据以一个简易问答系统为例,包括问题表...
    99+
    2024-04-02
  • 【史上最全】MySQL各种锁详解:一文搞懂MySQL的各种锁
    前言 锁在 MySQL 中是非常重要的一部分,锁对 MySQL 的数据访问并发有着举足轻重的影响。锁涉及到的知识篇幅也很多,所以要啃完并消化到自己的肚子里,是需要静下心好好反反复复几遍地细细品味。本文是对锁的一个大概的整理,一些相关深...
    99+
    2023-09-11
    数据库 mysql java 编程语言 面试
  • MySQL:七种 SQL JOINS 的实现(图文详解)
    MySQL:7种SQL JOINS的实现 前言一、图示表示二、代码举例1、INNER JOIN(内连接)2、LEFT JOIN(左连接)3、RIGHT JOIN(右连接)4、OUTER JOIN(全连接)5、LEFT EXCLUDI...
    99+
    2023-08-16
    mysql 数据库 sql 大数据
  • 深入理解mysql各种锁
    目录锁的概述锁分类对数据库操作的粒度分对数据操作的类型分mysql锁不同存储引擎支持锁级别锁介绍MyISAM表锁如何添加表锁加解锁锁竞争锁的使用情况InnoDB锁行锁锁升级间隙锁锁争...
    99+
    2024-04-02
  • 【MYSQL高级】Mysql 表的七种连接方式【附带练习sql】
    文章目录 连接七种JOIN介绍练习建表+存储数据笛卡尔积内连接左连接右连接A表独有B表独有全连接实现方式一:左连接+右连接+公共部分去重实现方式二:左连接+B独有 A独有+B独有 ...
    99+
    2023-09-17
    sql mysql 数据库
  • MySQL基础扎实——MySQL中有哪几种锁
    常见锁举例 在MySQL中,常见的锁包括以下几种: 表级锁(Table-level Lock):表级锁是对整张表进行锁定,可以分为两种类型: 共享锁(Shared Lock):也称为读锁(Read Lock),多个事务可以同时持有共...
    99+
    2023-08-30
    mysql 数据库
  • MySQL内连接和外连接及七种SQLJOINS的实现
    目录1. 内连接2.外连接左外连接:右外连接:满外连接:3. SQL99语法实现多表查询3.1 SQL99实现内连接3.2 SQL99语法实现外连接3.2.1 左外连接3.2.2 右...
    99+
    2023-03-23
    mysql 内连接 mysql外连接 sql joins
  • MySQL查询性能优化七种方式索引潜水
    目录前言: 有读者可能会一脸懵? 啥是索引潜水? 你给起的名字的吗?有没有索引蛙泳? 这个名字还真不是我起的,今天要讲的知识点就叫索引潜水(Index dive) 。 先要...
    99+
    2022-11-13
    MySQL查询性能优化 MySQL索引潜水
  • 怎样深入理解mysql各种锁
    怎样深入理解mysql各种锁,相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。锁的概述锁是计算机协调多个进程或线程并访问某一资源的机制在数据库中,除传统的计算机资源(如cpu、RA...
    99+
    2023-06-21
  • mysql表级锁的模式有几种
    本篇内容介绍了“mysql表级锁的模式有几种”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!1、表共享读锁,添加共享读锁的表不会阻塞其他ses...
    99+
    2023-06-20
  • PHP中header()的七种用法
    我们在实际开发中经常使用header()实现一些功能,这篇文章介绍关于header()的7中用法,需要的伙伴的开参考一下。 PHP header()的7中用法: 1、跳转页面 可以使用header()...
    99+
    2023-09-09
    php 开发语言
  • MySQL内连接和外连接及七种SQL JOINS的实现
    目录1. 内连接2.外连接左外连接:右外连接:满外连接:3. SQL99语法实现多表查询3.1 SQL99实现内连接3.2 SQL99语法实现外连接3.2.1 左外连接3.2.2 右外连接3.2.3 满外连接4.总结:七...
    99+
    2023-03-23
    mysql 内连接 mysql外连接 sql joins
  • Java七种常用设计模式
    1、单例模式(Singleton Pattern) 单例模式是(Singleton Pattern)Java中最常用的设计模式之一,它保证一个类仅有一个实例,并提供一个全局访问点。 实现单例模式的核心是将类的构造方法私有化,以防止外部直接通...
    99+
    2023-08-16
    java 设计模式 单例模式
  • Vista破解激活七种方法
    1、替换法 原理:用替换vista的一些许可文件的办法来用测试版序列号激活vista,是最早出现的办法 缺点:许可变为测试版,有时间限制 2、kms私服激活法 原理:不是去微软的官方服务器激活,而是去私人架设的服务器激活...
    99+
    2023-05-24
    Vista 破解激活 武器 方法
  • 七种常用的设计模式
    常用的七种设计模式:单例模式、工厂方法模式、抽象工厂模式、代理模式、装饰器模式、观察者模式和责任链模式。 设计模式分类 设计模式根据工作的目的,分为创建型模式、结构型模式和行为型模式三类。 创建型模式:单例模式、工厂方法模式、抽象工厂模式、...
    99+
    2023-08-31
    设计模式 java 单例模式
  • mysql锁的两种不同状态是什么
    本文小编为大家详细介绍“mysql锁的两种不同状态是什么”,内容详细,步骤清晰,细节处理妥当,希望这篇“mysql锁的两种不同状态是什么”文章能帮助大家解决疑惑,下面跟着小编的思路慢慢深入,一起来学习新知识吧。状态锁说明包括意向共享锁和意向...
    99+
    2023-06-30
  • 深入解析MySQL中的各种锁机制
    MySQL 各种锁详解一、引言在并发访问中,数据库需要使用锁来保护数据的一致性和完整性。MySQL 提供了多种类型的锁,包括共享锁、排他锁、意向共享锁、意向排他锁等。本文将使用具体的代码示例介绍并解析这些锁的使用方式和特点。二、共享锁(Sh...
    99+
    2023-12-21
    MySQL - 事务 - 行锁 - 表锁
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作