MySQL 9.0 发行说明
当 死锁检测 启用 (默认情况下) 时,InnoDB
会自动检测事务 死锁 并回滚一个或多个事务以打破死锁。 InnoDB
尝试回滚较小的事务,事务的大小由插入、更新或删除的行数决定。
如果 InnoDB
监控器输出的 LATEST DETECTED DEADLOCK
部分包含一条消息,指出 LOCK TABLE WAITS-FOR 图中搜索太深或太长,我们将回滚以下事务,则表明等待列表上的事务数量已达到 200 的限制。 超过 200 个事务的等待列表将被视为死锁,尝试检查等待列表的事务将被回滚。 如果锁定线程必须查看等待列表上事务拥有的超过 1,000,000 个锁,也会发生相同的错误。
InnoDB
了解表锁,前提是 innodb_table_locks = 1
(默认情况下) 且 autocommit = 0
,并且上面的 MySQL 层了解行级锁。 否则,InnoDB
无法检测到 MySQL LOCK TABLES
语句设置的表锁或其他存储引擎(而非 InnoDB
)设置的锁参与的死锁。 通过设置 innodb_lock_wait_timeout
系统变量的值来解决这些情况。
有关组织数据库操作以避免死锁的技术,请参阅 第 17.7.5 节,“InnoDB 中的死锁”.
在高并发系统中,死锁检测会导致许多线程等待同一锁时速度变慢。 有时,禁用死锁检测并依赖于 innodb_lock_wait_timeout
设置,以便在发生死锁时回滚事务,可能会更高效。 可以使用 innodb_deadlock_detect
变量禁用死锁检测。