要正确避免竞争条件,您可以使用LOCK TABLE
和事务以确保结果一致。
在您的查询中
UPDATE items SET itemcode=CONCAT('XYZ',(SELECT COUNT(*) as ctr FROM items
WHERE itemcode!=''),'GZ') WHERE itemid=123;
您正在选择具有给定属性的记录items
SELECT COUNT(*) as ctr FROM items WHERE itemcode!=''
然后将 123 与 XYZGZ 相关itemcode
联itemid
。
您也可以使用UPDATE JOIN
between items
and来做到这一点ctr
:
UPDATE items JOIN (
SELECT CONCAT('XYZ', COUNT(*), 'GZ') AS newcode FROM items
WHERE itemcode!='') AS dummy
SET itemcode = dummy.newcode WHERE itemid = 123;
或者在 MySQL 中(并使用 LOCK TABLES),您可以SELECT
将计数计入一个临时变量,然后分配itemcode
给该变量:
mysql> CREATE TABLE items ( itemid integer, itemcode varchar(32) );
mysql> INSERT INTO items VALUES ( 1, 'one' ), ( 2, 'two' ), ( 123, 'and 123');
mysql> LOCK TABLE items WRITE;
mysql> BEGIN WORK;
mysql> SELECT COUNT(*) INTO @x FROM items WHERE itemcode != '';
mysql> UPDATE items SET itemcode=CONCAT('XYZ',@x,'GZ') WHERE itemid = 123;
mysql> COMMIT WORK;
mysql> UNLOCK TABLES;
mysql> SELECT * FROM items;
+--------+----------+
| itemid | itemcode |
+--------+----------+
| 1 | one |
| 2 | two |
| 123 | XYZ3GZ |
+--------+----------+
3 rows in set (0.00 sec)
一种更短的方法,无需显式锁定:
mysql> BEGIN WORK;
mysql> SELECT COUNT(*) INTO @x FROM items WHERE itemcode != '' FOR UPDATE;
mysql> UPDATE items SET itemcode=CONCAT('XYZ',@x,'GZ') WHERE itemid = 123;
mysql> COMMIT WORK;