我正在使用 MySQL 5.1.73 和 InnoDB
我有一个非常慢的 UPDATE 查询(大约 10 秒),其中更改的行数(通常)为零(如果有几行更改,则需要大约相同的时间):
UPDATE job_queue SET state=4 WHERE error_counter>=5 AND state=1;
Query OK, 0 rows affected (9.33 sec)
但是,相应的 SELECT 相当快:
SELECT id FROM job_queue WHERE error_counter>=5 AND state=1;
Empty set (0.03 sec)
EXPLAIN SELECT id FROM job_queue WHERE error_counter>=5 AND state=1;
+----+-------------+-----------+-------+--------------------------------------------+---------------------+---------+------+-------+--------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-----------+-------+--------------------------------------------+---------------------+---------+------+-------+--------------------------+
| 1 | SIMPLE | job_queue | index | Allinone,state_timeout,state_error_counter | state_error_counter | 5 | NULL | 13515 | Using where; Using index |
+----+-------------+-----------+-------+--------------------------------------------+---------------------+---------+------+-------+--------------------------+
如您所见,这是(应该是?)一个索引查询,在一个不太大的数据库上(大约 9000 行,虽然它确实包含一些 blob,所以总数据库大小约为 800MB)。
问题是:
- 为什么更新这么慢?
- 我该如何调试它?
- 我怎样才能加快速度?
更新:我在使用 MySQL 5.5.35(Debian wheezy 默认)的不同服务器上尝试了相同的数据库。查询还是快,更新还是慢,更新还是没有解释……我可能会尝试从dotdeb升级到mysql 5.6,或者试试mariadb。:)
更新 2:我尝试了不同的行格式(动态和压缩),但也没有(明显)更快。
更新3:我更新到MySQL 5.6.17(来自dotdeb),性能大体相同,但我终于得到了更新的解释:
EXPLAIN UPDATE job_queue.job_queue SET state=4 WHERE error_counter>=5 AND state=1;
+----+-------------+-----------+-------+---------------+---------+---------+------+-------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-----------+-------+---------------+---------+---------+------+-------+-------------+
| 1 | SIMPLE | job_queue | index | NULL | PRIMARY | 8 | NULL | 70222 | Using where |
+----+-------------+-----------+-------+---------------+---------+---------+------+-------+-------------+
这只证实了一直以来可能被怀疑的东西:UPDATE 没有使用任何索引。所以问题仍然存在:为什么?
我将尝试创建一个产生这种行为的最小示例;也许在这个过程中,我会找到一些答案......