黄东旭解析 TiDB 的核心优势
588
2023-06-10
别废话,各种SQL到底加了什么锁?
有朋友留言,问能不能花2分钟讲讲,MySQL的各类SQL语句,究竟加了什么锁?
额,MySQL加的锁,和事务隔离级别相关,又和索引相关,尝试花2分钟讲讲看。
画外音:这2分钟需要的辅助知识,都已经附带了链接,贴心吧!
第一类,普通select加什么锁?
(2)在串行化(Serializable)这种事务的隔离级别下,普通select会升级为select ... in share mode;
【快照读】辅助阅读:《InnoDB,并发如此之高的原因》
第二类,加锁select加什么锁?
加锁select主要是指:
select ... for updateselect ... in share mode
(1)如果,在唯一索引(unique index)上使用唯一的查询条件(unique search condition),会使用记录锁(record lock),而不会封锁记录之间的间隔,即不会使用间隙锁(gap lock)与临键锁(next-key lock);
【记录锁,间隙锁,临键锁】辅助阅读:《InnoDB里的七种锁》
举个栗子,假设有InnoDB表:
t(id PK, name);
表中有三条记录:
shenjianzhangsanlisi
SQL语句:
select * from t where id=1 for update;
只会封锁记录,而不会封锁区间。
(2)其他的查询条件和索引条件,InnoDB会封锁被扫描的索引范围,并使用间隙锁与临键锁,避免索引范围区间插入记录;
第三类,update与delete加什么锁?
(1)和加锁select类似,如果在唯一索引上使用唯一的查询条件来update/delete,例如:update t set name=xxx where id=1;也只加记录锁;
(2)否则,符合查询条件的索引记录之前,都会加排他临键锁(exclusive next-key lock),来封锁索引记录与之前的区间;
(3)尤其需要特殊说明的是,如果update的是聚集索引(clustered index)记录,则对应的普通索引(secondary index)记录也会被隐式加锁,这是由InnoDB索引的实现机制决定的:普通索引存储PK的值,检索普通索引本质上要二次扫描聚集索引。
【索引底层实现】辅助阅读:《索引,底层是如何实现的?》
【聚集索引与普通索引的实现差异】辅助阅读:《InnoDB,聚集索引与普通索引有什么不同?》
第四类,insert加什么锁?
同样是写操作,insert和update与delete不同,它会用排它锁封锁被插入的索引记录,而不会封锁记录之前的范围。
同时,会在插入区间加插入意向锁(insert intention lock),但这个并不会真正封锁区间,也不会阻止相同区间的不同KEY插入。
【插入意向锁】辅助阅读:《InnoDB里的七种锁》
了解不同SQL语句的加锁,对于分析多个事务之间的并发与互斥,以及事务死锁,非常有帮助。
画外音:文章的参考资料为MySQL官网,以及楼主对MySQL的理解,版本基于5.6,欢迎探讨。
希望这2分钟,大家有收获。
来源链接:
版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。