2015-05-04 23 views
3

早上好,帶條件的外鍵關係

我有一個帶有ID和類型的主表。根據類型的不同,我有兒童表使用這個ID作爲外鍵來確保完整性。例如,對於主表:

master_ID, type 
11, A 
12, B 
13, A 

對於名爲Child_A的子表,它存儲類型A的附加數據;

Child_A_ID, FK_master_ID, .... 
1, 11, .... 
2, 13, .... 

當我的子表中存在相應的記錄時,如何防止我的主表中的類型更改爲不同的值。我的參照完整性目前保持不變,但在A類信息中存儲Child_A信息是沒有意義的,而主表中的記錄是不同類型的。

編輯:具有與所述2點的屬性(ID和類型),並重覆在每個子表的類型的外鍵

將是唯一的解決辦法?例如,爲child_A表;

Child_A_ID, FK_master_ID, type, .... 
1, 11, A, .... 
2, 13, A, .... 

希望它很清楚。

西爾

+0

你能提供一個例子嗎?您是否試圖表示如果ID在主表中發生了變化,並且子表中還有記錄? – murtazat

+0

@ murtazat否將保留主表中的ID,並保持子表的完整性。這是改變導致我問題的類型屬性的可能性。 – sylvain77

+0

即使您更改主表中的父鍵的數據類型,我認爲子表的參照完整性將由數據庫維護。那麼,爲什麼你擔心數據類型的變化?我不確定你的要求,但通常關心的是在子表中有孤兒引用。是否有必要在父表和父表中都保持相同的數據類型? – murtazat

回答

0

您可以創建一個使用user defined function,以確定是否id的值被包含在相關類型表check constraint

ALTER TABLE MasterTable 
    ADD CONSTRAINT CHK_MasterTable_Type 
    CHECK(dbo.fn_check_IdBelongsToType(master_ID, type) = 0) 

,並在功能本身,你做這樣的事情:

CREATE FUNCTION fn_check_IdBelongsToType (
    @master_ID int, 
    @type char(1) 
) 
RETURNS int 
AS 
BEGIN 
    IF @Type = 'A' AND EXISTS (
     SELECT 1 
     FROM Child_A 
     WHERE FK_master_ID = @master_ID 
    ) RETURN 1 

    IF @Type = 'B' AND EXISTS (
     SELECT 1 
     FROM Child_B 
     WHERE FK_master_ID = @master_ID 
    ) RETURN 1 

    IF @Type = 'C' AND EXISTS (
     SELECT 1 
     FROM Child_C 
     WHERE FK_master_ID = @master_ID 
    ) RETURN 1 

    -- after testing all child tables, return 0 to indicate that the value was not found 
    RETURN 0 

END