当前位置: 首页 > java >正文

MySQL 锁学习笔记

1.Mysql中有哪几种锁?

按作用范围划分:

1.全局锁:作用在整个数据库实例上的锁;

2.表锁:作用在表上的锁,主要有意向锁,表共享锁,表排他锁以及自增锁;

3.行锁:作用在行上的锁,MyISAM 不支持,InnoDB 支持,主要分为记录锁,间隙锁,临键锁;

按兼容性划分:

1.共享锁(S锁,读锁):只允许其他事务都上共享锁,只能读取数据,不能改写数据;

2.排他锁(X锁,写锁):不允许其他事务上任何锁,只能获取锁的事务读取和改写数据;

特殊锁:

1.自增锁:只用于自增列的锁,属于表锁,瞬发锁,只占用一小段时间,是为了保证自增的插入顺序。

2.全局锁,表级锁和行级锁了解吗?有什么区别?

首先就是作用范围不用,顾名思义;

再者就是不同的引擎所支持的锁级别不同,MyISAM 不支持 行锁,InnoDB 支持 行锁;

接着就是包含的锁不同,表锁有意向锁,表共享锁,表排他锁以及自增锁,而行锁有记录锁,间隙锁,临键锁,插入意向锁;

3.InnoDB 行锁的具体类型

InnoDB 包含的行锁主要有:

1.记录锁:只对具体的记录加锁;

2.间隙锁:对某一个范围加锁;

3.临键锁:则是记录锁和间隙锁的结合体;

4.意向插入锁:是一个特殊的间隙锁,只与间隙锁和临键锁阻塞,插入意向锁只与行级锁(间隙锁/临键锁)交互,与表级锁无直接关系。

4.意向锁有什么作用?插入意向锁和意向锁的区别?

意向锁主要是表级别的意向共享锁,意向排他锁以及行级别的意向插入锁;

1.表意向锁:

表级别的意向锁主要是为了平衡多粒度锁的性能,当有事务要对表里的行上锁,则先会获取表的意向锁,再上行锁,这样做的好处是当有另一个事务需要对表上锁时,并不需要遍历整个数据表判断是否有上行锁才能上表锁,而是直接通过表的意向锁判断是否可以上表锁,可以是何种表锁;

同一个表允许有多个事务获取意向共享锁和意向排他锁,有意向共享锁的表只能上表共享锁,有意向排他锁的表不能说任何表共享锁和排他锁。

2.意向插入锁:

意向插入锁只与间隙锁和临键锁阻塞。同一个范围的意向插入锁可以被多个事务获取,只要没有唯一值约束阻塞或者与间隙锁和临键锁阻塞,插入都可以执行成功,是为了解决重复读隔离级别下的幻读问题,意向插入锁和临键锁的联用才是解决在当前读环境下,重复读幻读问题的具体原理。

5.为什么会锁升级?锁升级的原理又是什么?

因为行锁粒度细所以内存,cpu 等资源开销大,所以当某个事务的行锁超过一定阈值时,行锁的收益小于表锁,所以需要升级锁,行锁升级到表锁后不会降级;

锁升级是为了降低系统因大量行锁而产生的内存和 CPU 开销。当一个事务持有的行锁超过 InnoDB 内部设定的阈值(大约 20,000 个),InnoDB 会尝试将这些行锁升级为表锁。升级过程会尝试获取表锁,成功后释放已有行锁,所有锁控制转由表锁进行。锁升级是单向的,一旦升级不会自动降级为行锁。

6.共享锁和排他锁的区别?

共享锁和排他锁即可以是表级别也可以是行级别;

共享锁下只允许读取数据,可以有多个事务同时获取,排他锁下允许读取和改写数据,但是当且仅当一个事务获取;

共享锁通过 LOCK ... READ 和 for share 指令上锁,排他锁通过 LOCK ... WRITE 和 for update 指令上锁;

7. 可重复读只有一次 Readview 怎么还会幻读呢?

可重复读隔离级别确实只创建一个 ReadView,因此对于快照读不会产生幻读。但在当前读(如 SELECT ... FOR UPDATE、UPDATE)中,InnoDB 是基于最新数据而不是快照进行访问,此时可能出现幻读。为了防止幻读,InnoDB 在 Repeatable Read 隔离级别下使用 Next-Key Lock(记录锁 + 间隙锁)锁定查询范围,从而避免其他事务插入幻行。

8.悲观锁与乐观锁区别是什么?

悲观锁:假设并发冲突一定会发生,先加锁再操作,mysql 内置锁都是悲观锁;

乐观锁:假设并发冲突很少发生,先操作再检查, 通常通过版本号、时间戳、CAS 等机制实现。

9.MySQL 实现不同隔离级别的原理,以及 MVCC 和锁的转换过程是什么?

不同隔离级别的实现原理:

1. Read Uncommitted(读未提交):不使用 MVCC,所有读操作不加锁也不判断版本,可以读到其他事务尚未提交的数据(脏读);

2. Read Committed(读已提交):使用 MVCC:每次 SELECT 都读取最新提交版本,每次读取时重新构造快照(Read View),可以防止脏读,但不可重复读;

3. Repeatable Read(可重复读,MySQL 默认):使用 MVCC,一个事务在开始时创建一次 Read View,整个事务周期内都用这个版本读,所以实现可重复读,同一行多次查询结果一致;幻读也可以通过(间隙锁/临键锁+意向插入锁)避免:修改/插入带条件的记录时加锁范围覆盖可能的“幻行”

4. Serializable(可串行化):所有读都加共享锁(S),所有写都加排他锁(X),强一致性但并发最低。

MySQL 的隔离级别通过 MVCC 和锁机制共同实现。对于读操作,InnoDB 主要依靠 MVCC 快照来提供一致性视图,实现不同隔离级别;对于写操作,使用行锁、间隙锁等方式来避免冲突。MVCC 通过隐藏列和 Undo Log 构建出数据的多个版本,快照读无需加锁即可保证事务一致性。而在显式加锁读或写操作中,InnoDB 会切换为锁机制,保证隔离性和一致性。

10. 死锁检测与处理流程

锁是指两个或多个事务在执行过程中,因竞争资源而互相等待,导致永远无法继续执行的现象。

InnoDB 通过构建等待图的方式进行死锁检测,当检测到死锁时,会自动回滚其中一个事务来解除死锁,优先选择开销最小的事务回滚。死锁检测是实时的,在事务加锁等待时触发,而不是依赖超时机制。

事务 A 请求锁 → 判断锁被事务 B 持有 → 标记为等待 → 构建等待图 → 检查是否成环。

http://www.xdnf.cn/news/14168.html

相关文章:

  • 计算机网络-自顶向下—第二章应用层-重点复习笔记
  • 在C++中的封装(Encapsulation)
  • Linux学习笔记:PCIe内核篇(1):初始化与枚举流程
  • 第1章 C# 和 .NET 框架 笔记
  • MCP简介和应用
  • 第十七章 Linux之大数据定制篇——Shell编程
  • ES知识合集(四):高级篇
  • 20250614让NanoPi NEO core开发板在Ubuntu core16.04系统下使用耳机播音测试
  • 「Linux文件及目录管理」目录结构及显示类命令
  • Python虚拟环境的使用
  • SpringBoot源码解析(十一):条件注解@ConditionalOnClass的匹配逻辑
  • 如何调优Kafka
  • LeetCode 第71题 简化路径(繁琐)
  • thinkphp8提升之查询
  • Nature Machine Intelligence 北京通研院朱松纯团队开发视触觉传感仿人灵巧手,实现类人自适应抓取
  • 开心灿烂go开发面试题
  • 如何自动化测试 DependencyMatcher 规则效果(CI/CD 集成最佳实践)
  • 免费OCPP协议测试工具
  • FreeRTOS定时器
  • C++/OpenCV地砖识别系统结合 Libevent 实现网络化 AI 接入
  • 如何写出优秀的单元测试?
  • 17.vue.js响应式和dom更新
  • java33
  • Java重构实战:小步快跑的高效策略分析
  • 【嵌入式硬件实例】-555定时器实现烟雾和易燃气体泄露检测
  • JAVA-springboot 异常处理
  • 15故障排查
  • CAD中DWG到DXF文件解析(一)
  • ELK日志文件分析系统——E(Elasticsearch)
  • 【算法深练】二分答案:从「猜答案」到「精准求解」的解题思路