SQL中的复杂外键约束

SQL中的复杂外键约束,sql,sql-server-2005,tsql,foreign-keys,constraints,Sql,Sql Server 2005,Tsql,Foreign Keys,Constraints,有没有一种方法可以使用SQLServer2005定义约束,从而不仅确保外键存在于另一个表中,而且还满足特定条件 例如,假设我有两个表: Table A -------- Id - int FK_BId - int Table B -------- Id - int Name - string SomeBoolean - bit 我是否可以定义一个约束,即sayd FK_BId必须指向表B中的记录,并且表B中的记录必须具有SomeBoolean=true?提前感谢您提供的任何帮助。我认为您要查

有没有一种方法可以使用SQLServer2005定义约束,从而不仅确保外键存在于另一个表中,而且还满足特定条件

例如,假设我有两个表:

Table A
--------
Id - int
FK_BId - int

Table B
--------
Id - int
Name - string
SomeBoolean - bit

我是否可以定义一个约束,即sayd FK_BId必须指向表B中的记录,并且表B中的记录必须具有SomeBoolean=true?提前感谢您提供的任何帮助。

我认为您要查找的内容超出了外键的范围,但您可以执行签入触发器、存储过程或代码

如果可能的话,我会说您可以使用
ID
SomeBoolean
将其设置为复合外键,但我认为它实际上并不关心值是什么。

在某些数据库中(我无法检查SQL Server),您可以添加一个引用其他表的检查约束

ALTER TABLE a ADD CONSTRAINT fancy_fk
CHECK (FK_BId IN (SELECT Id FROM b WHERE SomeBoolean));

我不认为这种行为是标准的。

您可以在
(Id,SomeBoolean)
上使用复合键来强制执行业务规则,在
表a中引用此项,并在
上使用
检查
约束来确保它始终为真。顺便说一句,我建议避免使用
BIT
,而是使用
CHAR(1)
进行域检查,例如

CHECK (SomeBoolean IN ('F', 'T'))
表结构可以如下所示:

CREATE TABLE B
(
 Id INTEGER NOT NULL UNIQUE, -- candidate key 1
 Name VARCHAR(20) NOT NULL UNIQUE,  -- candidate key 2
 SomeBoolean CHAR(1) DEFAULT 'F' NOT NULL
    CHECK (SomeBoolean IN ('F', 'T')), 
 UNIQUE (Id, SomeBoolean) -- superkey
); 

CREATE TABLE A 
(
 Ib INTEGER NOT NULL UNIQUE, 
 FK_BId CHAR(1) NOT NULL, 
 FK_BSomeBoolean CHAR(1) DEFAULT 'T' NOT NULL
    CHECK (FK_BSomeBoolean = 'T')
 FOREIGN KEY (FK_BId, FK_BSomeBoolean)
    REFERENCES B (Id, SomeBoolean)
);

触发器是在这样复杂的情况下确保数据完整性的唯一方法。@HLGEM-我是这么想的,但我上次使用SQL Server已经有一段时间了。@HLGEM:您可以使用DRI级别的超级键(根据onedaywhen的回答),而不会出现任何代码错误:在此上下文中不允许子查询。只允许使用标量表达式。我会将
A
中的列设为计算列,而不是使用check约束,但这只是一种味道/风格。