【问题标题】:MySQL Select works fine but Delete hangs indefinitely based on the position of GROUP BYMySQL Select 工作正常,但 Delete 根据 GROUP BY 的位置无限期挂起
【发布时间】:2019-05-09 14:55:30
【问题描述】:
select * from table1 where ID in (
    select min(a.ID) from (select * from table1) a group by id_x, id_y, col_z having count(*) > 1)

上述查询在 2.2 秒内运行,返回四个结果。现在,当我将select * 更改为delete 时,它会无限期挂断。

delete from table1 where ID in (
    select min(a.ID) from (select * from table1) a group by id_x, id_y, col_z having count(*) > 1)

如果我在别名选择查询中移动group by 子句的位置,它将不再挂起。

delete from table1 where ID in (
    select a.ID from (select min(ID) from table1 group by id_x, id_y, col_z having count(*) > 1) a)

为什么会挂起?尽管(select * from table1) 提取了数百万条记录,但查询似乎并没有停止执行几个小时。任何人都可以解释是什么使查询变得混乱吗?这让我感到困惑,因为选择查询工作正常,而删除查询挂起。

编辑: 我的重点是它为什么挂起。我已经发布了工作正常的解决方法。但是为了开发预防系统,我需要找到它的根本原因..

【问题讨论】:

  • MySQL 在优化WHERE ID IN (SELECT ...) 方面很差劲。请改用JOIN
  • 你几天前也问过同样的问题吗?我确定我记得最近回答过这样的问题,但我现在找不到了。我回答后你删了吗?
  • 如果您认为它不应该作为重复而关闭,您应该请求重新打开它,而不是再次发布相同的问题。
  • 我已经请求通过两次编辑重新打开另一个问题。然而,它似乎从未引起人们的注意。你还没有回答另一个问题。另外,另一个问题不是重复的

标签: mysql sql


【解决方案1】:

使用JOIN 代替WHERE ID IN (SELECT ...)

DELETE t1
FROM table1 AS t1
JOIN (
    SELECT MIN(id) AS minId
    FROM table1
    GROUP BY id_x, id_y, col_z 
    HAVING COUNT(*) > 1) AS t2
ON t1.id = t2.minId

我认为您的查询没有得到优化,因为它必须在每次删除后重新计算子查询,因为删除一行可能会更改该组的 MIN(id)。使用JOIN 只需要进行一次分组和聚合。

【讨论】:

  • 感谢您解释每次删除后如何重新计算min。删除min 评估后它工作正常。
【解决方案2】:

试试这个:

delete t
    from table1 t join
         (select min(id) as min_id
          from table1
          group byid_x, id_y, col_z
          having count(*) >= 2
         ) tt
         on tt.min_id = t.id;

也就是说,您可能不想只删除最小 id。我猜你想保留最新的ID。如果是这样:

delete t
    from table1 t left join
         (select max(id) as max_id
          from table1
          group byid_x, id_y, col_z
          having count(*) >= 2
         ) tt
         on tt.max_id = t.id
    where tt.max_id is null;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-09-18
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多