没有一种万能的解决方案可以满足您的所有需求。但是我以前见过的一个是
3) 为将共享关系的项目引入一个基表:
CREATE TABLE Entities (
EntityID int not null primary key,
EntityType varchar(10) not null,
constraint CK_EntityTypes CHECK (EntityType in ('Person','Place')),
constraint UQ_Entities_WithTypes UNIQUE (EntityID,EntityType)
)
然后构建您的 People 和 Places 表:
CREATE TABLE People (
PersonID int not null PRIMARY KEY,
EntityType AS CAST('Person' as varchar(10)) persisted,
...Other columns...
constraint FK_People_Entities FOREIGN KEY (PersonID,EntityType) references Entities (EntityID,EntityType)
)
CREATE TABLE Places (
PlaceID int not null PRIMARY KEY,
EntityType AS CAST('Place' as varchar(10)) persisted,
...Other columns...
constraint FK_Places_Entities FOREIGN KEY (PlaceID,EntityType) references Entities (EntityID,EntityType)
)
(我不确定Entities 在考虑地点时是否完全正确 - 一个更好的名字可能会向您推荐)。
然后您可以让Pictures 仅引用EntityID。
否则,如果我必须在 1 和 2 之间进行选择,我通常会推荐 1。除非涉及的“类型”数量变大,否则它仍然不会使 Pictures 表太宽,并且正如你'已经观察到,如果有必要,您至少可以使用正常的 FK 机制来强制执行级联。
4) 如果Pictures 目前只是一个非常裸的表,也许查询是否应该有 一个 图片表,或者每个类型一个。人物图片和地点图片是否会经常一起查询(即使是,基于UNION ALL 的查询是否会隐藏您使用单独表格的事实)?