2010-09-08 102 views
0

在我的數據庫過程中,我們用書(數據庫系統 - 整本書),它說,下面是標準的SQL有效create table語句:子查詢中的元組約束DB2

CREATE TABLE Participants (
    meetid INT NOT NULL, 
    -- ... 
    CONSTRAINT RoomConstraint 
     CHECK (1 >= ALL (SELECT num FROM Numbers) 
); 

但是DB2抱怨並給出了20個可能的解釋,說明爲什麼這個聲明失敗。

那麼,DB2不支持元組約束中的子查詢嗎?如果不是,TRIGGER是實施子查詢約束的唯一解決方案嗎?

更新:我發現這個鏈接,指出這是不可能的:http://bytes.com/topic/db2/answers/837390-can-constraint-replace-trigger

但同樣是一個觸發器的唯一出路? (我試圖執行一個關係,其中一個屬性可以參考兩個不同的表(它不是我的數據庫))

更新2:它不無ALL工作,要麼:

CREATE TABLE Foo (
    meetid INT NOT NULL, 
    CHECK (meetid IN (SELECT meetid FROM Foo))); 

更新3:的想法是,我想它引用類似下面兩個表的外鍵:從本質上講

Table Participants (pid, ...) 
Table Rooms (room, ...) 
Table People (userid, ...) 

,一個pid不得以任何滾裝存在oms(屬性室)或People(屬性用戶標識)中。我可以使用行約束來檢查pid是否在Rooms或People中 - 但DB2不會讓我。 (我知道有很多其他東西來限制模擬外鍵)

+0

請發佈真正的DDL。您的更新#2顯示了一個表格,您希望在插入它之前檢查meetid是否已存在於同一個表格中?你如何插入第一行? ;-) – 2010-09-09 20:22:02

+0

INTEGRITY OFF :)我只是想知道當我必須使用子查詢時是否有一個很好的替代行約束。真正的例子是漫長而愚蠢的(一個設計錯誤的數據庫),所以我認爲最好不要發表。但我會更詳細地解釋我想要的內容(請參閱2秒內的更新3) – 2010-09-09 20:44:39

回答

0

ALL()不是標準SQL ** - 它是一個T-SQL擴展。 DB2不支持這一點。

我不確定你想用你的約束來做什麼 - 它看起來像你試圖確保Numbers表中的每個num值小於或等於1.如果這實際上是在這種情況下,您應該在Numbers表上添加約束條件,而不是在參與者上添加約束條件。

** SQL92標準,我不相信它被添加到SQL99或SQL2003

+0

請參閱更新2.約束只是假人。 – 2010-09-08 15:33:02

1

如何實現SQL Server中的可選(備用)外鍵約束檢查

create function dbo.meetidinmeetings(@meetid) 
returns bit 
as 
begin 
declare @return bit 
as 
if exists(select 1 from meetings where meetid = @meetid) 
set @return =1 
else 
set @return = 0 
return @return 
end 

然後...

CREATE TABLE Foo (
meetid INT NOT NULL, 
ismeeting bit NOT NULL DEFAULT 0 

ALTER TABLE FOO 
ADD CONSTRAINT CHK_FOO_MEETID 
CHECK ((ismeeting = 0) or (ismeeting = 1 and dbo.is_meetidinmeetings(meetid) = 1)))