Pro "dotaz neaktualizuje správně řádky":
Chcete aktualizovat sloupec b
na minimum z b
pro všechny řádky se stejným a
Navrhli jste použít následující JOIN
jak to udělat:
UPDATE test.tem t1
JOIN test.tem t2
ON t1.a = t2.a
SET t1.b = t2.b
WHERE t1.b > t2.b
OR t1.b IS NULL;
Na rozdíl od toho, co si možná myslíte, že JOIN
neprovede 1-1 JOIN
. Ve skutečnosti je to mnoho k mnoha JOIN
od jak jsem řekl včera
v klauzuli spojení nepoužíváte primární klíč (ani nenull jedinečný klíč).
Ve skutečnosti tento dotaz přepíšete jako SELECT
pravděpodobně vám pomůže pochopit problém:
SELECT t1.a as t1a, t1.b as t1b, t2.a as t2a,t2.b as t2b FROM tem t1 JOIN tem t2
ON t1.a = t2.a
WHERE t1.b > t2.b
OR t1.b IS NULL;
+------+---------+------+--------+
| T1A | T1B | T2A | T2B |
+------+---------+------+--------+
| 1 | (null) | 1 | 2 |
| 1 | 2 | 1 | 1 |
| 1 | (null) | 1 | 1 |
| 1 | (null) | 1 | (null) |
+------+---------+------+--------+
http://sqlfiddle.com/#!2/856a7/8
Jak nyní uvidíte, řádek (1, null)
odpovídat (1, 1)
, (1, 2)
a (1, null)
. V závislosti na (nedeterministickém) pořadí provádění dotazu to může přiřadit kteroukoli ze tří možných hodnot pro b
(Tím si nejsem jistý, ale možná dokonce jej několik aktualizujete časy). Do jisté míry jste měli štěstí, že jste při testování našli „špatný“ výsledek!
Doufám, že to trochu více vysvětlí, proč váš dotaz nepřináší očekávaný výsledek. Protože UPDATE
příkazy neumožňují ORDER BY
ani GROUP BY
klauzule, jako já sám, abych našel "dobrý" výsledek, nevidím mnoho jiných možností než najít minimum první prostřednictvím dílčího dotazu...