【问题标题】:Mysql: Deadlock found when trying to get lock, need remove key?Mysql:尝试获取锁时发现死锁,需要删除密钥吗?
【发布时间】:2017-01-12 07:13:53
【问题描述】:

我在 Mysql 中统计页面浏览量统计数据,有时会出现死锁。

如何解决这个问题?也许我需要删除其中一个键?

但是阅读性能会怎样呢?还是不影响?

表:

CREATE TABLE `pt_stat` (
  `stat_id` int(11) unsigned NOT NULL AUTO_INCREMENT,
  `post_id` int(11) unsigned NOT NULL,
  `stat_name` varchar(50) NOT NULL,
  `stat_value` int(11) NOT NULL DEFAULT '0',
  PRIMARY KEY (`stat_id`),
  KEY `post_id` (`post_id`),
  KEY `stat_name` (`stat_name`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8

错误:“尝试获取锁时发现死锁;尝试重新启动事务”。

UPDATE pt_stat SET stat_value = stat_value + 1 WHERE post_id = "21500" AND stat_name = 'day_20170111';

【问题讨论】:

    标签: mysql sql database


    【解决方案1】:

    在处理死锁时,首先要做的始终是查看您是否有复杂的事务相互死锁。这是正常情况。但是,根据您的问题,我假设更新语句位于其自己的事务中,因此从逻辑数据库的角度来看,写入之间没有复杂的相互依赖关系。

    某些多线程数据库(包括 MySQL)可能会因为同一查询的线程内的写入依赖性而导致单语句死锁。顺便说一句,MySQL 并不孤单。众所周知,MS SQL Server 在某些情况和工作负载中存在类似问题。问题(正如您似乎理解的那样)是更新索引的线程可能会因另一个更新索引的线程而死锁(请记住,InnoDB 表是具有包含行数据的叶节点的索引)。

    在这些情况下,您可以考虑做三件事:

    1. 如果问题不严重,那么最好的选择通常是重试事务以防死锁。
    2. 您可以减少后台线程的数量,但这会影响读写性能,或者
    3. 您可以尝试删除索引(键)。但是,请记住,MySQL 上的未索引扫描速度很慢。

    【讨论】:

      猜你喜欢
      • 2017-02-07
      • 2017-04-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-11-22
      相关资源
      最近更新 更多