重点:

维度          Java synchronized              MySQL InnoDB行锁
锁载体      Java 对象Object                  索引记录(数据行资源)
载体谁指定    开发者手动传入obj         SQL的where条件自动定位
竞争者         线程                                  事务
释放时机    代码块执行结束                  事务commit/rollback
兼容规则    排他,不支持共享锁           区分S共享 / X排他,支持共享共存

核心:where条件的字段没有建立索引,就会升级为表锁。

案例:共享锁共存。就是共享锁可以被多个事务同时持有。

死锁:

业务切记:先查后改的场景绝对不要用 lock in share mode,极易死锁,直接使用  for update 。
 

全局锁

锁住整个数据库实例

表级锁

表级锁分为表锁,元数据锁,意向锁。

表锁:

分为读锁和写锁

读锁:不阻塞dql,只阻塞其他客户端的dml/ddl,本客户端的dml/ddl好像直接失败。全部客户端可以dql,不可以dml/ddl。场景:只读,后续不用修改。如:财务月底对账,统计报表。

写锁:本客户端可以dql,dml/ddl。其他客户端不可以dql,dml/ddl。场景:库存,订单状态变更。

元数据锁:

意向锁:

意向锁之间不会互斥

事务a加了行锁,事务b想加表锁,就得一行一行扫描有没有行锁,性能不好。

有了意向锁,不需要逐行检查行锁的情况,优化了加表级锁的速度。

主要解决行锁和表锁的冲突问题。

行级锁

行级锁主要分为:行锁,间隙锁,临键锁。

索引结构:b+树结构

行锁:

不通过索引条件检索数据,行锁就会升级成表锁

间隙锁:

锁的是间隙,不锁对应的记录。

唯一索引,给不存在的记录加锁时,优化为间隙锁。

临键锁:

非唯一普通索引在进行等值匹配的时候,会把该行以及该行的前后间隙都锁上。

没匹配到呢?加间隙锁呗

唯一索引使用范围查询也会加上临键锁

总结:

唯一索引:--》等值查询

只有唯一索引+等值=查询,才存在降级。命中->记录锁,未命中->间隙锁。

任意索引 范围查询:

不降级,使用临键锁,向后延伸还会追加间隙锁。

更多推荐