2017-06-28 32 views
2

對於CARS,有兩列MAKE和MODEL,我希望強制對於某些特定的MAKE值,它們的MODEL值必須是唯一的(假設這是一個Oracle數據庫)。在Oracle數據庫的表上行上實現唯一性

例如,我想強制重複福特而不是豐田。我不想讓'F150'MODEL和'Ford'MAKE組成一行。但是,使用'Rav4'MODEL和'Toyota'MAKE可以有兩排。 F150'MODEL','Ford'MAKE和'F150'MODEL'和'Toyota'MAKE'也是可以的。

我一直在研究與觸發器,約束或索引的各種策略,但我還沒有發現任何東西,會給我我需要的控制水平。

謝謝!

回答

2

您可以創建一個獨特的基於函數的索引執行的唯一性(品牌,型號),對僅時許=「福特」:

create table cars (make varchar2(255) not null, model varchar2(255) not null); 

create unique index ford_index on cars (
    case make 
    when 'Ford' then make 
    else null 
    end, 
    case make 
    when 'Ford' then model 
    else null 
    end ); 


insert into cars (make, model) values ('Ford', 'F150'); 
insert into cars (make, model) values ('Ford', 'Fiesta'); 
insert into cars (make, model) values ('Toyota', 'Camry'); 
insert into cars (make, model) values ('Toyota', 'Camry'); 
insert into cars (make, model) values ('Ford', 'F150'); --- FAILS with unique constraint violation 

ford_index指數(品牌,型號)只有化妝=」福特' - 其他所有東西都不在索引中,因此不受唯一性限制。

+0

但是,如果有二十八個必須執行唯一性的製造商,以及另外三十六個不需要唯一性的製造商,那麼您會如何編寫這個?如果需要唯一性的製作清單隨着時間而改變,它將如何維持? – mathguy

+0

@mathguy - 可能我會爲每個需要模型唯一性的make創建一個索引。既然我們在談論汽車製造商,我預計製造數量會相當低。 – user1041892

+0

謝謝!在這種情況下,我沒有想過使用病例陳述。這當然是我見過的最好的方式。 對我來說不幸的是,我不得不將這添加到已經有重複項的表中(以防止未來的重複),但是對於約束上的'DEFFERED NOVALIDATE'選項,似乎沒有任何索引等效項。 – JKuester

0

創建物化視圖,並在提交時進行快速刷新。 MV的定義可能只是select make, model from <your_table> where make in (select make from <small_table>)<small_table>將列出您想要執行此唯一性的製造商。然後在物化視圖中創建一個唯一索引(make, model)

每當嘗試使用make 'Ford'進行重複時,MV將在提交時刷新。 MV的變化將被拒絕,這反過來會導致原始的COMMIT失敗。

+0

如果您將創建語句添加到您的文章中,這將會很好。 – miracle173

+0

@ miracle173 - 創建物化視圖語句是微不足道的。更重要的是,必須首先創建MV日誌。 – mathguy

+0

快速刷新的mviews不能有選擇列表子查詢。 – eaolson

相關問題