在mysql8.X中執行如下語句:
DELETE
FROM
`zjs-quality-control-qupai`.unsign_wocode
WHERE
id IN (
SELECT
a.id
FROM
`zjs-quality-control-qupai`.unsign_wocode a,
( SELECT wocode, max( in_time ) maxintime FROM `zjs-quality-control-qupai`.unsign_wocode GROUP BY wocode HAVING count(*) > 1 ) b
WHERE
a.wocode = b.wocode
AND a.in_time < b.maxintime
);
報如下錯誤:
DELETE
FROM
`zjs-quality-control-qupai`.unsign_wocode
WHERE
id IN (
SELECT
a.id
FROM
`zjs-quality-control-qupai`.unsign_wocode a,
( SELECT wocode, max( in_time ) maxintime FROM `zjs-quality-control-qupai`.unsign_wocode GROUP BY wocode HAVING count(*) > 1 ) b
WHERE
a.wocode = b.wocode
AND a.in_time < b.maxintime
)
> 1093 - You can't specify target table 'unsign_wocode' for update in FROM clause
> 時間: 0.002s
通過去官網mysql錯誤代碼查詢錯誤代碼1093得到信息如下:
Error number: 1093
; Symbol: ER_UPDATE_TABLE_USED
; SQLSTATE: HY000
Message: You can't specify target table '%s' for update in FROM clause
This error occurs for attempts to select from and modify the same table within a single statement. If the select attempt occurs within a derived table, you can avoid this error by setting the derived_merge
flag of the optimizer_switch
system variable to force the subquery to be materialized into a temporary table, which effectively causes it to be a different table from the one modified. See Section 8.2.2.4, “Optimizing Derived Tables, View References, and Common Table Expressions with Merging or Materialization”.
這個錯誤發生的原因是在單個sql語句中查詢並且修改了同一個表。如果嘗試從派生表中查詢,可以通過設置系統變量optimizer_switch的derived_merge屬性去強迫將子查詢的結果存儲到臨時表,從而避免這種錯誤發生。
下面是解決方案,不是通過上面的方式,而是網上的說法,在子查詢外再寫一層查詢
正確的源代碼如下:
DELETE
FROM
`zjs-quality-control-qupai`.unsign_wocode
WHERE
id IN (
SELECT
new.id
FROM
(
SELECT
a.id
FROM
`zjs-quality-control-qupai`.unsign_wocode a,
( SELECT wocode, max( in_time ) maxintime FROM `zjs-quality-control-qupai`.unsign_wocode GROUP BY wocode HAVING count(*) > 1 ) b
WHERE
a.wocode = b.wocode
AND a.in_time < b.maxintime
) new
);
最後,關於臨時表、派生表的解釋請參考如下地址:
https://blog.csdn.net/weixin_44863976/article/details/102789392