ray88’s diary

お仕事で困ったとき用の自分用の覚書

SQL指南書 比較述語とNULL④ 限定述語とNULL(ALLとANY)

■限定述語
 SQLには ALL と ANY の2つの限定述語がある。
 ANY は IN と同値のため、あまり使用されない
■ALL
 ALLは比較述語と併用し「~全てと等しい」や「~全てよりもおおきい」という意味を表す

【具体例】
以下のテーブルよりNULLを排除したケースで「Bクラスの東京在住の誰よりも若いクラスAの生徒」を取得するSQLを考える

--/* B クラスの東京在住の誰よりも若いA クラスの生徒を選択する(p.59) */
SELECT *
  FROM Class_A
 WHERE age < ALL ( SELECT age
                     FROM Class_B
                    WHERE city = '東京' );

■パターン1:NULL値がデータにない場合

出力結果

■パターン2:NULL値がデータに存在する場合
※パターン1と同じSQL文でも1行も出力されない
 理由:ALL述語が条件をANDで連結した倫理式の省略形として定義されているため。

出力結果

1行も出力されないのは以下のようなステップで評価を行っているから

--1.サブクエリを実行して年齢リストを取得
SELECT *
	FROM class_a
WHERE age < ALL(22,23,NULL);
--2.ALL述語をANDで同値変換
SELECT *
	FROM class_a
WHERE (age < 22) AND (age < 23) AND (age < NULL);
--3.NULLに < を適用すると unknown になる
SELECT *
	FROM class_a
WHERE (age < 22) AND (age < 23) AND unknown;
--4.AND演算子にunknownが含まれると結果がtrueにならない
SELECT *
	FROM class_a
WHERE false または unknown;