为什么MySQL在高并发下建议关闭死锁检测_权衡性能开销与系统稳定性

风墨君_4489

风墨君_4489

2026-05-19

1001人浏览

原创

MySQL死锁检测不可关闭,它是保障事务正确性的安全阀;关闭后死锁不被发现,事务将等待超时(默认50秒)才回滚,导致响应延迟、线程堆积和错误掩盖,真正根因是热点行争用、索引缺失与事务设计缺陷。

为什么mysql在高并发下建议关闭死锁检测_权衡性能开销与系统稳定性

MySQL 的死锁检测不能也不该被“建议关闭”——它不是性能开关,而是事务正确性的安全阀。所谓“高并发下建议关闭”,是把症状当病因、用掩盖代替治理的危险误解。

innodb_deadlock_detect=OFF 真的能提升性能?

关掉后 CPU 使用率可能确实下降,但代价是:所有死锁不再被主动发现,事务会卡在 LOCK WAIT 状态,直到 innodb_lock_wait_timeout(默认 50 秒)超时才回滚。你看到的“快”,只是错误被延迟暴露了。

  • 应用层收不到 Deadlock found when trying to get lock,而是等半分钟才收到 Lock wait timeout exceeded
  • 活跃等待线程堆积,SHOW PROCESSLIST 里大量 updating 或 Locked 状态,实际已无进展
  • SHOW ENGINE INNODB STATUS 中 LATEST DETECTED DEADLOCK 消失,但 TRANSACTIONS 列表里 waiting 数持续上涨

真正吃 CPU 的从来不是检测逻辑本身

死锁检测函数 lock_deadlock_occurs() 的单次调用开销是纳秒级的。真正让 CPU 爆表的,是高并发下大量事务反复争抢同一行(比如库存扣减、计数器更新),导致每次加锁都要遍历一个越来越大的等待图(wait-for graph)——这个图的节点数 ≈ 活跃事务数,边数 ≈ 锁等待链长度,检测复杂度接近 O(N²)。

  • 现象:CPU 100% 时,innodb_row_lock_waits 持续上涨,但 innodb_row_lock_time_avg 很低(说明不是锁持有久,而是抢锁失败太频繁)
  • 根因不是检测,而是热点行 + 无序访问 + 间隙锁扩散(尤其在 REPEATABLE READ 隔离级别下)
  • 关检测就像拔掉警报器来“解决”火灾报警声——火还在烧

为什么有人觉得“关了更稳”?

那通常是因为他们已在外围做了足够强的兜底:应用层捕获死锁错误并指数退避重试(最多 3 次)、事务粒度极小、热点数据已分片、且业务允许短暂不一致(如浏览量、点赞数)。此时关检测只是把“10ms 失败 + 重试”换成“50s 超时 + 重试”,对整体成功率影响不大,却避免了检测 CPU 雪崩拖垮整个实例。

MySQL
MySQL

编写正确的MySQL查询,避免字符集、索引和锁方面的常见陷阱。

下载
  • 这种做法只适用于非核心路径(如日志写入、异步触发),绝不适用于支付、订单、账户余额等强一致性场景
  • 关检测必须配合 innodb_lock_wait_timeout=5(而非默认 50),否则用户感知延迟不可控
  • innodb_rollback_on_timeout 必须保持 OFF(默认值),否则超时回滚不通知客户端,应用可能误判操作成功

比开关参数重要一百倍的事

真正决定死锁频率的,永远是 SQL 怎么写、索引怎么建、事务怎么切、数据怎么分片。

  • 确保所有 UPDATE/SELECT FOR UPDATE 的 WHERE 条件都命中索引,避免全表扫描触发间隙锁
  • 多行更新强制按主键升序处理:SELECT id FROM t WHERE id IN (1002,1001) ORDER BY id FOR UPDATE
  • 把热点行拆成多个逻辑单元(如用 MOD(user_id, 64) 分 64 个计数器 shard)
  • 把高频单行更新合并为批量语句:INSERT INTO t VALUES (...), (...) ON DUPLICATE KEY UPDATE ...
  • 非必要不升级隔离级别:READ COMMITTED 下间隙锁关闭,锁范围更小,死锁概率天然更低

死锁不是 bug,是并发访问模式与锁机制碰撞出的信号灯。盯着 innodb_deadlock_detect 调参数,不如花十分钟看一眼 SHOW ENGINE INNODB STATUS 里的等待图链条——那里面藏着最真实的业务逻辑缺陷。

相关文章

数码产品性能查询
数码产品性能查询

该软件包括了市面上所有手机CPU,手机跑分情况,电脑CPU,电脑产品信息等等,方便需要大家查阅数码产品最新情况,了解产品特性,能够进行对比选择最具性价比的商品。

下载

相关标签:

mysql

本站声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

相关专题

更多
mysql修改数据表名
mysql修改数据表名

MySQL修改数据表:1、首先查看数据库中所有的表,代码为:‘SHOW TABLES;’;2、修改表名,代码为:‘ALTER TABLE 旧表名 RENAME [TO] 新表名;’。php中文网还提供MySQL的相关下载、相关课程等内容,供大家免费下载使用。

2023.06.20

2413

6

MySQL创建存储过程
MySQL创建存储过程

存储程序可以分为存储过程和函数,MySQL中创建存储过程和函数使用的语句分别为CREATE PROCEDURE和CREATE FUNCTION。使用CALL语句调用存储过程智能用输出变量返回值。函数可以从语句外调用(通过引用函数名),也能返回标量值。存储过程也可以调用其他存储过程。php中文网还提供MySQL创建存储过程的相关下载、相关课程等内容,供大家免费下载使用。

2023.06.21

1459

5

mongodb和mysql的区别
mongodb和mysql的区别

mongodb和mysql的区别:1、数据模型;2、查询语言;3、扩展性和性能;4、可靠性。本专题为大家提供mongodb和mysql的区别的相关的文章、下载、课程内容,供大家免费下载体验。

2023.07.18

855

5

mysql密码忘了怎么查看
mysql密码忘了怎么查看

MySQL是一个关系型数据库管理系统,由瑞典MySQL AB 公司开发,属于 Oracle 旗下产品。MySQL 是最流行的关系型数据库管理系统之一,在 WEB 应用方面,MySQL是最好的 RDBMS 应用软件之一。那么mysql密码忘了怎么办呢?php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

2023.07.19

3392

5

mysql创建数据库
mysql创建数据库

MySQL是一个关系型数据库管理系统,由瑞典MySQL AB 公司开发,属于 Oracle 旗下产品。MySQL 是最流行的关系型数据库管理系统之一,在 WEB 应用方面,MySQL是最好的 RDBMS 应用软件之一。那么mysql怎么创建数据库呢?php中文网给大家带来了相关的教程以及文章,欢迎大家前来阅读学习。

2023.07.25

5828

4

mysql默认事务隔离级别
mysql默认事务隔离级别

MySQL是一种广泛使用的关系型数据库管理系统,它支持事务处理。事务是一组数据库操作,它们作为一个逻辑单元被一起执行。为了保证事务的一致性和隔离性,MySQL提供了不同的事务隔离级别。php中文网给大家带来了相关的教程以及文章欢迎大家前来学习阅读。

2023.08.08

1259

3

sqlserver和mysql区别
sqlserver和mysql区别

SQL Server和MySQL是两种广泛使用的关系型数据库管理系统。它们具有相似的功能和用途,但在某些方面存在一些显著的区别。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

2023.08.11

6111

4

mysql忘记密码
mysql忘记密码

MySQL是一种关系型数据库管理系统,关系数据库将数据保存在不同的表中,而不是将所有数据放在一个大仓库内,这样就增加了速度并提高了灵活性。那么忘记mysql密码我们该怎么解决呢?php中文网给大家带来了相关的教程以及其他关于mysql的文章,欢迎大家前来学习阅读。

2023.08.14

5282

7

mysql事务隔离级别
mysql事务隔离级别

mysql规范中定义了四种事务隔离级别,不同的隔离级别对事务的处理有所不同。本专题为大家提供mysql事务隔离级别相关的文章内容,大家可以免费体验。

2023.08.16

7094

11

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
PostgreSQL vs MySQL
PostgreSQL vs MySQL

共1课时 | 193人学习