Home
Posts
Tag
About
数据库中的几种锁
数据库中的几种锁
2018-03-20 11:12:27
#mysql
#数据库
#并发
#### 乐观锁&悲观锁 我理解的乐观(Optimistic )悲观(Pessimistic)指的是一种期望,在并发场景下读数据到回写的时间段内数据是否已变更的期望,乐观锁期望在数据读取完毕到回写回库中的时间段内该条数据不会发生变化,所以不进行加锁。若数据已经发生改变,需要业务逻辑中做异常处理。悲观锁的期望是会变更,所以先加锁再读取。 + ##### 乐观锁 在数据库内部update同一行的时候是不允许并发的。在提交数据更新之前,每个事务会先检查在该事务读取数据后,数据是否被修改过。如果已经修改,正在提交的事务会回滚。通常使用版本号或时间戳进行实现。通过在```update```的```where```条件中添加```version = old_version```或```update_time = old_Update_time```。 + ##### 悲观锁 所谓的"一锁二查三更新",通常来说由数据库提供支持。即```select … for update```。 --- #### 读写锁 读写锁,也称为共享锁&排他锁, + ##### 读锁(共享锁) 读锁在加锁之后并发会话可同时读取加锁数据,但不能进行更改 + ##### 写锁(排他锁) 加锁之后会锁定对应数据,并发其他会话不能读取数据,需要等待排他锁释放 --- #### 粒度 |引擎类型|行锁|表锁|页锁| |--| :--: | :--: | :--: | |MyISAM||Y(默认)|| |DBD||Y|Y(默认)| |InnoDB|Y(默认)|Y|| + ##### 表锁: 开销小,加锁快;不会出现死锁;锁定力度大,发生锁冲突概率高,并发度最低 + ##### 页锁: 开销和加锁速度介于表锁和行锁之间;会出现死锁;锁定粒度介于表锁和行锁之间,并发度一般 + ##### 行锁: 开销大,加锁慢;会出现死锁;锁定粒度小,发生锁冲突的概率低,并发度高。InnoDB行锁是通过给索引上的索引项加锁来实现的,这一点MySQL与Oracle不同,后者是通过在数据块中对相应数据行加锁来实现的。so **注意:select for update语句执行中所有扫描过的行都会被锁上,在mysql中用悲观锁务必要确定走了索引,而不是全表扫描** --- 参考资料: [【MySQL】悲观锁&乐观锁](https://www.cnblogs.com/zhiqian-ali/p/6200874.html) [MySQL学习之——锁(行锁、表锁、页锁、乐观锁、悲观锁等)](http://blog.csdn.net/mysteryhaohao/article/details/51669741)