0

给定这样的表,其中 x 和 y 具有唯一约束。

编号,x,y
1, 1,1
2, 1,2
3, 2,3
4, 3,5
..

我想使用 UPDATE 语句将一组行中的值 x 和 y 增加固定量。假设我将它们都增加 1,似乎 UPDATE 遵循 id 顺序并在用 1 2 更新行后给我一个错误,因为它与下一行 2 3 冲突,该行尚未更新为 3、4然而。

谷歌搜索,我找不到强制 UPDATE 使用订单的方法。反过来做对我的应用程序来说就足够了。我也确信整个更新后设置是一致的。

有什么解决办法吗?以某种方式强制订单进行更新,或者以任何方式使其将约束检查推迟到完成?

这适用于 Django 应用程序,并且与所有受支持的数据库兼容。我知道有些数据库有原子事务并且不会发生这个问题,有些数据库有避免这个问题的功能,但我需要一个严格标准的 SQL 解决方案。

4

2 回答 2

1

对于 PostgreSQL,您可以将主键约束定义为“可延迟”,然后仅在提交时对其进行评估。

在 PostgreSQL 中,这看起来像这样:

postgres=>create table foo (
postgres(>    id integer not null,
postgres(>     x integer,
postgres(>     y integer
postgres(>);
CREATE TABLE
postgres=>alter table foo add constraint pk_foo primary key (id) deferrable initially deferred;
ALTER TABLE
postgres=> insert into foo (id, x,y) values (1,1,1), (2,1,1), (3,1,1);
INSERT 0 3
postgres=> commit;
COMMIT
postgres=> update foo set id = id + 1;
UPDATE 3
postgres=> commit;
COMMIT
postgres=> select * from foo;
 id | x | y
----+---+---
  2 | 1 | 1
  3 | 1 | 1
  4 | 1 | 1
(3 rows)
postgres=>

对于 Oracle,这不是必需的,因为它将 UPDATE 语句评估为单个原子操作,因此可以立即使用。

于 2012-04-16T17:12:57.983 回答
0

为了参考起见,MS SQL Server 也不会出现这个问题。UPDATE 是单个原子操作。

ALTER TABLE [table_name]
ADD CONSTRAINT unique_constraint
UNIQUE(x)

ALTER TABLE [table_name]
ADD CONSTRAINT unique_constraint2
UNIQUE(y)

update [table_name]
set x = x+1,
y = y+1

应该完全没有问题。

于 2012-04-16T18:35:31.740 回答