MySQL连接更新运行缓慢

时间:2018-07-05 14:26:03

标签: mysql join sql-update

我正在运行MySQL 5.6.33,并且有一个运行缓慢的更新查询,我不明白为什么。

我有两个表:alltranscur中有35,908行,acctnumcust中有86,103行。

查询:

update alltranscur a inner join acctnumcust d
on a.acctNumber=d.acctNum
set
a.custID=d.custID

花费很长时间(5分58.29秒,匹配约22,000行)。我也将其写为:

update alltranscur a, acctnumcust d
set
a.custID=d.custID
where a.acctNumber=d.acctNum

具有相同的结果。

表的创建语句为:

CREATE TABLE `alltranscur` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`custID` varchar(200) DEFAULT NULL,
`acctNumber` int(11) DEFAULT NULL,
... other columns
PRIMARY KEY (`id`),
KEY `acctNumber` (`acctNumber`),
... other keys
CONSTRAINT `alltranscur_ibfk_8` FOREIGN KEY (`custID`) REFERENCES `custdata` (`custID`) ON UPDATE CASCADE
... other foreign keys
) ENGINE=InnoDB AUTO_INCREMENT=5226303 DEFAULT CHARSET=latin1

CREATE TABLE `acctnumcust` (
`acctnum` varchar(50) NOT NULL,
`custid` varchar(200) NOT NULL,
PRIMARY KEY (`acctnum`),
KEY `custid` (`custid`),
KEY `acctnum` (`acctnum`,`custid`),
CONSTRAINT `acctnumcust_ibfk_1` FOREIGN KEY (`custid`) REFERENCES `custdata` (`custID`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1

如果我

explain
update alltranscur a inner join acctnumcust d
on a.acctNumber=d.acctNum
set
a.custID=d.custID

我得到:

+----+-------------+-------+-------+-----------------+------------+---------+---------------+-------+-------------+
| id | select_type | table | type  | possible_keys   | key        | key_len | ref           | rows  | Extra       |
+----+-------------+-------+-------+-----------------+------------+---------+---------------+-------+-------------+
|  1 | SIMPLE      | d     | index | PRIMARY,acctnum | custid     | 202     | NULL          | 85152 | Using index |
|  1 | SIMPLE      | a     | ref   | acctNumber      | acctNumber | 5       | pcb.d.acctnum |     1 | Using where |
+----+-------------+-------+-------+-----------------+------------+---------+---------------+-------+-------------+

我以为MySQL会在acctnum上使用PRIMARY键,甚至可能在acctnum / custID上使用组合键。但事实并非如此。

这与这样的查询一样快吗?过去,我已经在类似大小的表上进行了联合更新,并且花费的时间并不长。我在这些桌子上缺少什么吗?有没有办法使其运行更快?

1 个答案:

答案 0 :(得分:2)

问题的根本原因很可能是您将两个表联接到具有不同数据类型的列上

`acctNumber` int(11) DEFAULT NULL,
`acctnum` varchar(50) NOT NULL,

where a.acctNumber=d.acctNum

这意味着MySQL无法直接使用索引并最终进行全表扫描。

将表acctnum中列acctnumcust的数据类型更改为INT(11),应该解决您的性能问题