为了在 postgres 中强制执行部分唯一性,创建部分唯一索引而不是显式约束是一种众所周知的解决方法,如下所示:
CREATE TABLE possession (
possession_id serial PRIMARY KEY,
owner_id integer NOT NULL REFERENCES owner(owner_id),
special boolean NOT NULL DEFAULT false
);
CREATE UNIQUE INDEX possession_unique_special ON possession(owner_id, special) WHERE special = true;
这将限制每个所有者在数据库级别拥有不超过一个特殊财产。显然不可能创建跨越多个表的索引,因此该方法不能用于在列存在于不同表中的超类型和子类型情况下强制执行部分唯一性。
CREATE TABLE possession (
possession_id serial PRIMARY KEY,
owner_id integer NOT NULL REFERENCES owner(owner_id)
);
CREATE TABLE toy (
possession_id integer PRIMARY KEY REFERENCES possession(possession_id),
special boolean NOT NULL DEFAULT false
);
如您所见,在此示例中,较早的方法不允许将每个所有者限制为不超过一个特殊玩具。假设每个财产都必须实现一个子类型,那么在 postgres 中强制执行此约束而又不显着改变原始表的最佳方法是什么?