面试题答案
一键面试容易导致死锁的常见操作或业务场景
- 并发竞争资源:多个事务同时对相同的一组数据行进行加锁操作,且加锁顺序不一致。例如,事务A先锁定行1,再尝试锁定行2;而事务B先锁定行2,再尝试锁定行1,就可能形成死锁。
- 锁范围过大:使用表级锁而非行级锁,或者在不必要的情况下使用大粒度的锁。例如,在更新少量数据时却对整个表进行加锁,这样会增加事务之间锁冲突的概率,容易导致死锁。
- 长时间持有锁:事务执行时间过长,长时间持有锁不释放,导致其他事务等待时间过长,增加死锁的可能性。比如,事务中包含复杂的计算或外部系统调用,使锁长时间无法释放。
- 嵌套事务:在一个事务中嵌套多个子事务,并且这些事务对相同资源进行加锁操作,若加锁顺序不当,也容易引发死锁。
MySQL内部检测死锁的机制
MySQL InnoDB存储引擎通过 死锁检测机制 来检测死锁。当事务请求的锁由于其他事务持有而不能立即获取时,InnoDB会将这个锁请求放入等待队列中。在等待过程中,InnoDB会定期检查等待队列,查看是否存在循环等待的情况(即死锁)。一旦检测到死锁,InnoDB会选择一个牺牲者(通常是回滚代价最小的事务),回滚该事务并释放其持有的锁,以打破死锁局面,让其他事务能够继续执行。