web-dev-qa-db-ja.com

外部キー列にNULLがあります

私はPostgreSQLでSIMPLEおよびFULLに一致する外部キーについて学習しており、次の思考プロセスが正しいかどうか疑問に思っています。

外部キーの参照列の少なくとも1つにNULL値が含まれると、参照されるテーブルへのリンクはありません。これは、3VLによると、NULLは別のNULL値と比較できないためです。これは、関連する列に少なくとも1つのNULL値を含む参照された行が更新または削除されるときに、定義されたカスケードアクション(_... DO DELETE_、_... DO SET NULL_、..)など)が更新または削除されないことを意味します。参照された行へのリンクはありません。より具体的には、テーブルA(x, y)からB(x, y)までの外部キーを想定します。 ABの両方にxyの行_(5, NULL)_が含まれている場合、NULLの行のANULLの行のBと等しくないため、リンクはありません。

これは正しいです?私はSQLに非常に慣れていないので、これを正しく理解したかどうか疑問に思っています。

6
Gnarfly

たしかにそれは正しいね。 Fiddle で小さな例を作成しました

create table p
( a int not null
, b int
, unique (a,b)
);

create table c
( a int not null
, b int
, constraint fk_p foreign key (a,b)
                  references p (a,b)
                      on delete cascade
                      on update cascade
);

-- insert data in parent:
insert into p (a,b) values (1,null);  -- ok
insert into p (a,b) values (1,null);  -- also ok. The constraint evaluates to null,
                                      -- which is ok. The rule is that it must not 
                                      -- evaluate to false

-- insert data in child
insert into c (a,b) values (1,null);  -- ok
insert into c (a,b) values (2,null);  -- also ok, foreign key evaluates to null. 
                                      -- So despite there is no 2 in
                                      -- parent this is ok

-- remove data from parent
delete from p;

-- all rows present in child
select * from c;

a   b
1   null
2   null 

Nullは、些細なことでも把握するのが少し難しいです。 nullを含む候補キーはお勧めしません。

5
Lennart