【问题标题】:MySQL UPDATE with JOIN extremely slowMySQL UPDATE 与 JOIN 非常慢
【发布时间】:2021-03-23 14:15:06
【问题描述】:

我主要处理 SQL 服务器 TSQL。我的任务是将 TSQL sproc 转换为 MySQL sproc。在 TSQL 中,以下小更新需要不到一秒钟的时间。 MySQL 中的相同更新需要 20 分钟或更长时间。

UPDATE MyTempTable 
INNER JOIN ZipCode on ZipCode.SourceZip = pSourceZip
                  AND ZipCode.DestZip = pDestZip
SET 
    CT = ZipCode.GD 
WHERE
    ZipCode.Updated >= DATE_ADD(CURDATE(), INTERVAL -365 DAY);

pSourceZippDestZip 是存储过程的参数。临时表中有 2 行。邮政编码中有 35,992,342。 ZipCode 在SourceZipDestZip 上有一个索引。我可以运行以下简单的选择并立即返回。 select * from ZipCode where SourceZip = pSourceZip and DestZip = pDestZip;我在更新中遗漏了什么?

【问题讨论】:

  • 对更新做一个解释,你就会看到瓶颈在哪里。
  • @Shadow 确实有帮助,谢谢!发布我自己的答案以帮助遇到此类问题的任何人。
  • 您可以向临时表添加索引,然后检查您的解释计划是否存在性能瓶颈

标签: mysql sql-update


【解决方案1】:

ZipCode需要

INDEX(SourceZip, Updated, DestZip)

而且数据类型非常匹配。某些不匹配是可以的,但 INT 与 VARCHAR 不匹配。

varchar_col = int-constant(如zip CHAR(5)zip = 12345)不能使用INDEX(zip)。将CHAR(5) 更改为MEDIUMINT 或将12345 更改为"12345"。 (或两者兼有)

在您的情况下,您将pSourceZip 作为存储例程的参数?那么它应该具有与ZipCode.SourceZip 相同的声明。 (至少都是 char 或两者都是 int。)

【讨论】:

    【解决方案2】:

    ZipCode 表将SourceZipDestZip 定义为varchar(5)。旧的 TSQL sproc 接受 zip 参数为int,所以我在 MySQL sproc 中做了同样的事情。我猜 MySQL 对类型转换没有那么宽容。我将 MySQL 参数切换为 varchar(5) 并立即执行更新。

    【讨论】:

    • 是的。我扩充了我的答案以澄清这一点。
    猜你喜欢
    • 2015-07-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-09-22
    • 2017-05-07
    • 1970-01-01
    • 1970-01-01
    • 2015-12-14
    相关资源
    最近更新 更多