2025/12/25 21:53:07
网站建设
项目流程
两学一做网站网址大全,北京王府井,域名已买 可以找其它人做网站吗,移动网站怎么登录在真实业务中#xff0c;你遇到的大多数 MySQL 性能问题、死锁问题#xff0c;几乎都与“锁”有关。但很多工程师对锁的理解停留在碎片层面#xff1a;
知道“行锁”“间隙锁”“next-key-lock”#xff0c;但不知道 SQL 是如何触发这些锁的、锁到底锁在哪里、为什么会锁这…在真实业务中你遇到的大多数 MySQL 性能问题、死锁问题几乎都与“锁”有关。但很多工程师对锁的理解停留在碎片层面知道“行锁”“间隙锁”“next-key-lock”但不知道SQL 是如何触发这些锁的、锁到底锁在哪里、为什么会锁这么多。这一篇文章我会用工程化思维带你一次性理解InnoDB 锁机制的全景图。看完以后你将具备✔ 能看懂锁的真实作用✔ 能从 SQL 推断出锁范围✔ 能解释死锁发生原因✔ 能在面试中条理清晰地讲出锁机制一、为什么 InnoDB 的锁机制这么复杂MySQL 采用MVCC 锁实现事务隔离其中最关键的隔离级别是RC读已提交RR可重复读默认RR 是企业最常见的隔离级别它要解决“幻读”问题。于是有了三个锁记录锁Record Lock间隙锁Gap LockNext-Key LockRecord Gap所有复杂问题都来自这个组合。二、InnoDB 的三种核心锁理解它们的作用和触发条件Record Lock真实行上的锁锁的对象一条真实存在的记录触发场景精确命中唯一索引例如SELECT * FROM user WHERE id 10 FOR UPDATE;只锁(10]—— 单条记录。特点不会锁间隙因此不会阻止插入。Gap Lock只锁“间隙”不锁数据作用阻止“间隙内插入新数据”防止幻读。例如索引中已有值10 --- 20 --- 30SQLSELECT * FROM user WHERE age 20 FOR UPDATE;Gap Lock 会锁住(20, 30) (30, ∞)重点Gap Lock 不锁记录只锁区间。Next-Key LockRecord Gap 的组合锁RR 下范围查询的默认锁模式(prev_key, record_key]例如假设索引有 10、20、30SELECT * FROM t WHERE age BETWEEN 15 AND 25 FOR UPDATE;锁住的区间(10,20] (20,30]作用✔ 锁住命中的记录✔ 锁住记录前的 gap → 阻止插入这就是为什么 RR 隔离级别能规避幻读。三、锁到底由哪些 SQL 触发“ SQL → 锁类型” 映射表SQL 场景索引情况锁类型原因WHERE id ?唯一键精确命中Record Lock不需要锁 gapWHERE id ?普通索引精确匹配但非唯一Next-Key Lock防止幻读WHERE age ?/ ?范围扫描Next-Key Lock必须锁 gapBETWEEN范围查询范围扫描Next-Key Lock防止插入无索引过滤全表扫描大量 Record Lock每条记录都会被锁LIKE %abc无法走索引表锁风险全表扫描一句话总结能精确锁住记录 → Record Lock需要范围扫描 → Next-Key Lock范围扫描一定会锁 gap → Gap Lock四、锁具体加在什么区间假设索引中有如下值10 ---- 20 ---- 30 ---- 40来看不同 SQL 加的锁WHERE id 20 FOR UPDATE锁(10, 20]但如果字段是主键/唯一键会优化成[20]WHERE id 20 FOR UPDATE锁(20,30) (30,40) (40,∞)WHERE id BETWEEN 15 AND 35 FOR UPDATE锁(10,20] (20,30] (30,40]无索引条件SELECT * FROM user WHERE namexxx FOR UPDATE;锁住所有记录[10], [20], [30], [40]→ 大量锁冲突发生的根源。五、总结InnoDB 的锁永远基于索引。无法精确匹配记录就会使用 Next-Key Lock。范围查询一定会带 gap 锁。掌握这三点后死锁、锁等待、幻读问题都能一眼看穿。