假設要實現約束的列名為C1, 所在表名為MyTable
(1)除了SQL SERVER 以外的大型數據庫都是允許 UNIQUE約束有多個空值的。
(2)SQL Server 2008中有了一個解決方案,那就是篩選索引。
CREATE UNIQUE NONCLUSTERED INDEX MyTable
ON MyTable(C1)
WHERE C1 is not null
GO
(3)SQL Server 2008以下版兩個方案
A、使用觸發器在插入和更新時控制
CREATE trigger Mytrigger on MyTable for insert, update as
BEGIN
IF (select max(cnt) from (select count(i.c1)
as cnt from MyTable, inserted i where MyTable.c1=i.c1 group
by i.c1) x) > 1
ROLLBACK TRAN
END
B、 在約束中使用自建函數來實現
創建驗證邏輯函數
CREATE FUNCTION [dbo].[fn_CK_MyTable_C1]()
RETURNS BIT
AS
BEGIN
IF(EXISTS(
SELECT 1
FROM MyTable AS a
WHERE (C1 IS NOT NULL) AND EXISTS
(SELECT 1 AS Expr1
FROM MyTable
WHERE (C1 IS NOT NULL) AND (C1 = a.C1) )
))
RETURN 0
RETURN 1
END
GO
在約束中引用函數:
ALTER TABLE test_tb
ADD CONSTRAINT CK_MyTable_C1 CHECK (dbo.fn_CK_MyTable_C1() = 1)
