死锁(一)前言

前言

    近期在工做在遇到了几个和之前本身理解的一些不同的死锁问题,所以想作一个mysql的死锁系列,梳理一下mysql引起死锁的一些场景,因为我的认知终归有限,本文所列的死锁场景不表明mysql所有的死锁触发缘由,但愿给其余同窗启示,如能在工做中刚好起到帮助做用,那就更好了。mysql

死锁是什么

    若是有多个事务,这里咱们暂定为两个,事务A须要请求锁lock_1,可是因为事务B占据着相关资源,致使事务A不能得到lock_1;同时,事务B请求锁lock_2,可是因为事务A占据着相关资源,致使事务B不能得到锁lock_2。为了避免让两个事务都这么长期hang着,这个时候mysql将会根据本身的一套规则选出开销最小的事务,将其回滚,这样,另一个事务就可以获取须要的锁资源继续执行了。sql

    以前不少文章都将死锁的概念阐述为这样,这里简单描述就是:若是事务A已经持有锁lock_1,但愿继续获取锁lock_2;同时,事务B已经获取锁lock_2,想继续获取锁lock_1,两个事务都占据着对方但愿获取的锁,因而产生死锁!spa

    若是按照第二种概念理解死锁的定义,核心思想就是死锁产生是由于双方事务想获取的锁都被对方事务占据着。这种理解其实有些片面,其实,死锁产生的缘由本质上是两个事务已经持有的锁资源之间的相互影响,即只要事务B持有的锁影响了事务A对相关锁的获取,同时事务A持有的锁影响了事务B对相关锁的获取,不管事务A想获取的锁此时是否被事务B占据着,此时都造成死锁!3d

 

为何要检测死锁

    若是没有死锁检测机制,若是发生了上面的场景,mysql该怎么解决,是的,可能你想到了,可使用锁超时,涉及相关的参数是innodb_lock_wait_timeout,可是这种方式是被动的,效率很低,相比之下,死锁检测就是更主动了,只要上面的说到的多事务互相hang住的场景一旦被mysql检测到,mysql就会主动回滚低开销事务。blog

 

死锁检测方法:

    mysql采用wait-for graph 原理来检测死锁,简单的说就是多事务之间在互相hang住的时候,若是等待资源的矢量,造成了闭合回路,那么此时就断定为死锁,下图就是这样的例子:事务

    事务1因为事务2已经持有的部分锁,致使不能获取相关的锁,矢量方向指向事务2。同理事务2,事务3,事务4,矢量方向最终在4个事物之间造成闭合环路,死锁造成。资源

 

 

 

 

  请你们理解上面的概念,接下来的文章中咱们将会用实际的例子来展示死锁产生的各类场景,在掌握了底层原理后,相信你们能以不变应万变it

相关文章
相关标签/搜索