2017-08-29 9 views
2

2つのテーブル(テーブル1とテーブル2)に関連していない行をカタログから選択したいとします。(...)以外のIDには制限がありますか? - NOT NOT EXISTS

カタログ内の行は、フィールドidAを使用するテーブルに関連しています。

私は、次のクエリを使用しています:

;with CTE(id) AS(
select distinct idA from Table1 
union 
select distinct idA from Table2 
) 
select * from Catalog where IdA NOT IN (select id from CTE) 

非常に奇妙な部分は、このクエリはどんな結果を返さないことです。

私はデCTEの後に次のクエリを使用している場合、それはいくつかの行

を返します
select Id from Catalog where not exists (select 1 from CTE where Catalog.IdA = CTE.Id); 

誰もがその理由が何であるかを知っていますか? AFAK両方のクエリは同等です。

もちろん、最初のクエリは2番目のクエリよりも遅いですが、それほど重要ではありません。重要なのは、これらのクエリが同じ結果を返さない理由です。

は、多分それは表1を超える390万行 しかしidAのためだけ139283異なる値を持っていることを言及することが重要です。 表2は、1つまたは複数のNULL値がNOT INサブクエリによって返された場合はすべてのヘルプやコメントが

+3

「NOT IN」サブクエリによって1つ以上のNULL値が返された場合、結果全体はNULL(不明)です。不明ではないため、条件が満たされず、行が返されません。 –

+0

@DanGuzmanが言ったことにタグを付けるために、サブクエリで返すカラムを明示したいのですが... 'exists()'を使用してください。 – scsimon

+0

@DanGuzmanあなたは絶対に正しいです!私がCTE内のクエリに「どこIdAがnullでない」と追加すると、問題は解決されます。あなたが答えを加えると私はそれを受け入れます – Ayorus

答えて

2

を理解されるであろう

のみ数千行を持って、述部の結果は、真または偽となしの行ではなく、不明です満足していない状態のために返された。この非直感的な動作を回避するには、NULL可能な式を使用してNOT INを避けるのが最善です。

もっと冗長にすると、関連するNOT EXISTSサブクエリは常にtrueまたはfalseを返し、NULLのgotchaを回避します。

関連する問題