我有一个汇总项目及其类别的表格。一个项目可以有多个类别。这是简化的模式和示例数据:
表名:xref,(itemID,catID)定义为主键
itemID | catID
-------+-------
4059 | 159
4059 | 219
我还有一个类别合并功能。执行此操作时,我还将源类别中链接的产品移动到目标(合并)类别。对于将项目从类别159移动到219,我使用这样的SQL:
UPDATE `xref` SET `catID` = 219 WHERE `catID` = 159
但更新失败,因为已经存在4059-219(PK约束)。
期望的结果是
itemID | catID
-------+-------
4059 | 219
我无法在数据库上使用存储过程或函数,但可以在我的应用程序中实现所需的步骤。
SELECT * FROM xref WHERE catID IN (159, 219) GROUP BY itemID HAVING COUNT(*) >= 2
是一种正确的方法吗?答案 0 :(得分:1)
我无法使用@ JNevill的方法,因为我事先并不知道受影响的项目ID。但这让我对这个两步解决方案有所了解。
UPDATE IGNORE `xref` SET `catID` = 219 WHERE `catID` = 159
DELETE FROM `xref` WHERE `catID` = 159
感谢所有其他答案/评论。
答案 1 :(得分:0)
尝试以下查询:
UPDATE `xref`
SET `catID` = 219
WHERE `catID` = 159
and `itemID` not in (select 'itemID'
from (select *from 'xref') x
where 'catID' = 219)
;
希望它有所帮助!
答案 2 :(得分:0)
这种方式会暂时删除您的约束以允许更新,然后将它们放回到最后。
如果您的数据库是生产数据库 TEST ON A COPY!
# set up tables for the purpose of this example
CREATE TABLE Item
(
ItemId INT,
ItemName VARCHAR(255),
PRIMARY KEY (ItemId)
);
CREATE Table Category
(
CatId INT,
CatName VARCHAR(255),
PRIMARY KEY (CatId)
);
CREATE TABLE xref
(
ItemId INT,
CatId INT,
PRIMARY KEY (ItemId,CatId),
FOREIGN KEY (ItemID) REFERENCES Item(ItemId),
FOREIGN KEY (CatId) REFERENCES Category(CatId)
);
# insert data for the purpose of this example
INSERT INTO Item
VALUES
(1,'Hammer'),
(2,'Chisel'),
(3,'Wrench');
INSERT INTO Category
VALUES
(159,'Tool'),
(219,'Toy'),
(3,'foo');
INSERT INTO xref
VALUES
(1,159),
(1,219),
(2,159),
(3,3);
START TRANSACTION;
# remove constraints so we can run the update
ALTER TABLE xref DROP FOREIGN KEY xref_ibfk_1;
ALTER TABLE xref DROP FOREIGN KEY xref_ibfk_2;
ALTER TABLE xref DROP PRIMARY KEY;
# Update the categories
UPDATE xref SET CatId = 219 WHERE CatId = 159;
# Copy the table into a tmep table but exclude duplicates we have created above
CREATE TEMPORARY TABLE IF NOT EXISTS xref_tmp AS (SELECT DISTINCT
ItemId,
CatId
FROM xref);
# Empty the original table
DELETE FROM xref;
# Copy the clean results back to the orginal table
INSERT INTO xref
SELECT * FROM xref_tmp;
# put our constaints back
ALTER TABLE xref ADD PRIMARY KEY (ItemId,CatId);
ALTER TABLE xref ADD FOREIGN KEY (ItemID) REFERENCES Item(ItemID);
ALTER TABLE xref ADD FOREIGN KEY (CatID) REFERENCES Category(CatID);
COMMIT