MyISAM 不需要意向锁,因其不支持事务和行级锁,仅使用简单表级锁且锁立即释放;意向锁是 InnoDB 为协调表锁与行锁而设计的轻量级元数据锁,用于快速判断锁冲突。

MyISAM根本没有事务,所以压根不需要意向锁
意向锁(IS 和 IX)是 InnoDB 为协调「表级锁」和「行级锁」共存而设计的轻量级元数据锁。它的存在前提是:事务可以同时持有表级锁(比如 DDL 操作需要的 MDL)和行级锁(比如 UPDATE ... FOR UPDATE),必须提前声明“我接下来要对这行加 X 锁”,否则表级写锁(如 ALTER TABLE)就无法安全地判断是否该阻塞。
MyISAM 完全不支持事务,也没有行级锁机制:UPDATE 或 INSERT 一执行就立即落盘、立即释放表锁,不存在“事务中先查再改”“锁持续到 commit”的语义。它只有两种自动加锁行为:
- SELECT → 自动加表级共享读锁(
READ LOCK),其他会话仍可读,但不能写 - UPDATE/DELETE/INSERT → 自动加表级独占写锁(
WRITE LOCK),期间整张表对所有读写都阻塞
因为 MyISAM 的锁生命周期极短、无嵌套、无跨语句延续性,根本不需要“预告意图”。它也不支持 START TRANSACTION,更不会出现“一个事务里先锁某几行、又想对整张表做结构变更”这种冲突场景。
InnoDB 的意向锁是行锁与表锁协作的“握手协议”
InnoDB 默认走行锁,但某些操作(如 ALTER TABLE、DROP TABLE)必须获取表级排他锁(MDL)。如果没有意向锁,当一个事务正在对某几行加 X 锁时,另一个事务想执行 ALTER TABLE,数据库只能暴力扫描全表看有没有行锁——成本太高,且破坏并发。
意向锁就是这个“轻量通告”:
- 事务准备对某行加
S锁前,先对整张表加IS锁 - 事务准备对某行加
X锁前,先对整张表加IX锁 -
IS和IX之间互相兼容,不阻塞彼此 - 但
IX与表级MDL写锁互斥,所以ALTER TABLE能立刻感知“有人正操作这表的行”,直接等待而非盲扫
换句话说:IS/IX 不是为锁行服务的,而是为“让表级锁能快速、安全地判断是否该等”服务的。
你执行 SHOW ENGINE INNODB STATUS 能看到意向锁,但 MyISAM 根本没这个字段
在 InnoDB 的锁信息输出里,你会看到类似这样的记录:
TABLE LOCK table `test`.`t1` trx id 12345 lock mode IX RECORD LOCKS space id 100 page no 3 n bits 72 index PRIMARY of table `test`.`t1` trx id 12345 lock_mode X locks rec but not gap
其中 lock mode IX 就是意向排他锁;而 MyISAM 压根没有 SHOW ENGINE 的锁状态视图,INFORMATION_SCHEMA.INNODB_TRX、INNODB_LOCKS 这些表也完全为空——因为它根本不维护事务级锁状态。
真正容易被忽略的是:即使你只用 InnoDB,如果 SQL 没走索引(比如 WHERE name = 'xxx' 但 name 没索引),InnoDB 可能放弃行锁,退化为全表扫描+逐行加锁,效果接近 MyISAM 的表锁。这时意向锁依然存在,但实际并发收益归零——锁机制再精巧,也救不了没索引的查询。


















