2013-03-15 44 views
2

我在我的數據庫中的表上有一個檢查約束。我對檢查的理解是它爲表中的記錄設置了一個合理的條件。爲什麼t-sql允許我違反使用UDP的檢查約束?

USE [myDB] 
GO 

ALTER TABLE [dbo].[myTable] WITH CHECK ADD CONSTRAINT [oneProgramPerTest] CHECK (([dbo].[howManyProgPerTest]([TestId])<(2))) 
GO 

ALTER TABLE [dbo].[myTable] CHECK CONSTRAINT [oneProgramPerTest] 
GO 

但我能夠對打破約束的表進行更新。更新後,此查詢返回9條記錄:

select COUNT (*) from myDB.dbo.myTable where myDB.[dbo].[howManyProgPerTest](testID)>1 

可能會發生什麼?

回答

4

由於這個原因,謹防在檢查約束中使用UDF。 This blog post describes your issue.總結:

(A UDF)將在表面上做的工作,只要你INSERT到 表。但是,如果更新一行並僅將其他列設置爲從0到1的 行,則不會檢查檢查約束。

優化器足夠聰明,可以理解更新不會改變我們在CHECK約束中引用的任何內容,那麼爲什麼 會檢查約束?

這裏最終結果就是約束不會做我們想要的 做的。 改用觸發器(或其他方法)

(強調)

0

如果我可以根據您的約束的名稱,你想確保有每個測試只是一個計劃?如果程序和測試都在同一個表中可用,請添加唯一約束。