最新下载
热门教程
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
MySQL锁有哪些类型以及如何区分
时间:2026-08-28 09:26:49 编辑:袖梨 来源:一聚教程网
InnoDB默认用行锁,但仅当WHERE条件命中索引时生效;无索引则退化为表锁;意向锁(IS/IX)是自动加的表级预告锁,不阻塞其他意向锁,但与显式表锁互斥,并指示表内存在行锁。
行锁、表锁、意向锁,到底谁在锁什么
InnoDB 默认用行锁,但不是所有 UPDATE/SELECT FOR UPDATE 都真锁一行——它只在 WHERE 条件命中索引时生效。没索引?直接退化成表锁,整张表卡住,其他事务全等。
意向锁(IS/IX)是表级“预告”,不阻塞别的意向锁,但会和真正的表锁(LOCK TABLES ... WRITE)互斥。它本身不拦人,但它是行锁存在的信号灯:看到 IX,你就知道“这张表里肯定有某几行被 X 锁了”。
- 查当前有没有行锁冲突?跑
SELECT * FROM sys.innodb_lock_waitsG,看blocking_query字段 - 想确认是不是表锁?
SHOW OPEN TABLES WHERE In_use > 0,In_use值非 0 就说明被显式锁住了 - 意向锁没法手动加,它是自动的:你一执行
UPDATE t SET x=1 WHERE id=5(id 是主键),InnoDB 就先悄悄加IX,再给那行加X
共享锁 S 和排他锁 X 的实际表现差异
S 锁(SELECT ... LOCK IN SHARE MODE)允许多个事务同时读同一行,但谁都改不了;X 锁(UPDATE、DELETE、SELECT ... FOR UPDATE)是独占的,别人连读带写全被挡在外面。
关键区别不在语法,而在兼容性:两个事务对同一行加 S 锁可以并存;一个加了 S,另一个想加 X?立刻阻塞;两个都加 X?也立刻阻塞。这就是锁等待超时(Lock wait timeout exceeded)的常见起点。
-
S锁不会阻止其他事务加S,但会阻止X;X锁阻止一切(S和X) -
SELECT不加LOCK IN SHARE MODE或FOR UPDATE时,默认走 MVCC,不加任何行级锁 - 在 RR 隔离级别下,
X锁实际是Next-Key Lock(记录锁 + 间隙锁),比如WHERE id > 10 AND id ,不仅锁住匹配的行,还锁住 (10,20) 这个区间,防幻读
死锁报错 vs 锁等待超时,一眼识别法
报错信息就是最准的诊断入口:ERROR 1213 (40001): Deadlock found when trying to get lock 是死锁;ERROR 1205 (40001): Lock wait timeout exceeded 是锁等待超时——注意错误码不同,别搞混。
死锁发生快(毫秒级)、自动回滚一个事务;锁等待默认卡 50 秒才报错,且只卡住当前事务,不影响别人。如果线上频繁出现后者,大概率是大事务没提交、或某条 SQL 没走索引导致锁范围过大。
- 立刻查死锁现场:
SHOW ENGINE INNODB STATUSG,重点看LATEST DETECTED DEADLOCK段落 - 查当前锁等待:
SELECT * FROM performance_schema.data_locksG(MySQL 8.0+)或information_schema.INNODB_TRX+INNODB_LOCK_WAITS - 别依赖
SHOW PROCESSLIST,它只显示连接状态,看不到锁关系
间隙锁和临键锁最容易被忽略的触发条件
间隙锁(Gap Lock)只在 RR 隔离级别、且 WHERE 条件是范围查询(>、、BETWEEN)或非唯一索引等值查询时才激活。它不锁数据行,只锁“空隙”,目的是防止幻读——但副作用是,两个事务同时执行 SELECT ... FOR UPDATE WHERE name='alice'(name 无唯一索引),可能互相锁住同一个间隙,然后 INSERT 冲突,引发死锁。
临键锁(Next-Key Lock)是 RR 下的默认行为,等于记录锁 + 左边间隙锁,区间左开右闭。比如索引值为 [1,5,10],WHERE id > 5 AND id 会锁住 (5,10),而 WHERE id = 5(主键)只锁住记录本身,不锁间隙。
- 唯一索引 + 精准等值查询(如
WHERE id=5)→ 只有记录锁,无间隙锁 - 非唯一索引 or 范围查询 → 必然带间隙锁,哪怕没数据也会锁住空隙
- 想关间隙锁?设隔离级别为
READ-COMMITTED,但代价是可能读到幻读
真正难的不是记住锁类型,而是理解“同一句 SQL 在不同索引、不同隔离级别、不同 WHERE 条件下,锁的类型和范围可能完全不同”。一次没走索引的 UPDATE,就能让行锁变成表锁;一个没注意的范围查询,就可能把间隙锁变成死锁导火索。
相关文章
- Tplink企业版路由器WiFi名称的默认设置介绍(Tplink企业版路由器WiFi名称的默认设置是什么) 09-06
- Tplink路由器灯常亮无法上网的原因分析(如何解决Tplink路由器灯常亮无法上网的问题) 09-06
- Tplink千兆企业级路由器自动重启的作用和优势介绍(如何设置Tplink千兆企业级路由器自动重启功能) 09-06
- 一根天线的tplink路由器有哪些(一根天线的Tplink路由器的特点和优势介绍) 09-06
- tplink路由器外网访问不了nas(Tplink路由器外网访问NAS的原因分析) 09-06
- Tplink无法搜到路由器的原因分析(如何解决Tplink无法搜到路由器的问题) 09-06