初めに
データベースとSQLは現在のデータサイエンスに必須な知識・スキルの1つ。その基礎を
を基に学んできた。
この知識をより昇華させて「SQL中級者になりたい!」ため、同じ著者の
を参考に、更なるSQLの知識を拡充していこう。
前回
4. 3値論理とNULL
は他のプログラミング言語とは異なり、3値論理を採用している。すなわちの3値からなる論理型を採用している。これはを採用したことで導入せざるを得なかったものだった。
4.1 NULLとは
は値でも変数でもない値が無いことを表す「記号」である。そのため型という概念が無く、これに対する比較述語(等号や不等号)はになるために値を判定することができない*1。
4.2 unknown
3値論理では論理表が以下のとおりになる:
t |
u |
f |
t |
u |
f |
|||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|
t |
f |
t |
t |
u |
f |
t |
t |
t |
t |
|||
u |
u |
u |
u |
u |
f |
u |
t |
u |
u |
|||
f |
t |
f |
f |
f |
f |
f |
t |
u |
f |
4.3 NOT INとNOT EXISTS
パフォーマンスのチューニングのためにとを置き換えることがある。しかしこれらの結果が一致しない場合がある。
Class_A | Class_B | ||||||
name(名前) |
age(年齢) |
city(住所) |
name(名前) |
age(年齢) |
city(住所) |
||
---|---|---|---|---|---|---|---|
ブラウン |
22 |
東京 | 斎藤 |
22 |
東京 | ||
ラリー |
19 |
埼玉 | 田尻 |
23 |
東京 | ||
ボギー |
21 |
千葉 | 山田 |
東京 | |||
和泉 |
18 |
千葉 | |||||
武田 |
20 |
千葉 | |||||
石川 |
19 |
神奈川 |
これらのテーブルに対して「Bクラスの東京在住の生徒と年齢が一致しないAクラスの生徒」を選択するクエリを考える。
-- これは上手くいかない SELECT * FROM Class_A WHERE age NOT IN (SELECT age FROM Class_B WHERE city = '東京')
これは途中でとなるため、上手くいかなくなる。
正しい結果を得るには、句を用いる。
-- これは上手くいかない SELECT * FROM Class_A AS A WHERE age NOT EXISTS (SELECT age FROM Class_B AS B WHERE A.age = B.age AND B.city = '東京')
4.4 限定述語とNULL
はとという2つの限定述語を持っている*2。
は比較述語と併用して「~すべてと等しい」や「~すべてよりも大きい」の意味を持つ。
Class_A | Class_B | ||||||
name(名前) |
age(年齢) |
city(住所) |
name(名前) |
age(年齢) |
city(住所) |
||
---|---|---|---|---|---|---|---|
ブラウン |
22 |
東京 | 斎藤 |
22 |
東京 | ||
ラリー |
19 |
埼玉 | 田尻 |
23 |
東京 | ||
ボギー |
21 |
千葉 | 山田 |
18 |
東京 | ||
和泉 |
18 |
千葉 | |||||
武田 |
20 |
千葉 | |||||
石川 |
19 |
神奈川 |
-- Bクラスの東京在住の誰よりも若いAクラスの生徒を選択する SELECT * FROM Class_A WHERE age < ALL (SELECT age FROM Class_B WHERE city = '東京')
これもと同じようにを持っていると上手く動作しない。
4.5 極値関数とNULL
極値関数で限定述語を代用する場合、厳密には全く同一の結果を返すわけではないことに注意する。
-- SELECT * FROM Class_A WHERE age < (SELECT MIN(age) FROM Class_B WHERE city = '東京')
基本的には同じような結果を返す一方で、述語(または関数)の入力が空集合だと結果が異なる。述語を用いるとすべての行を選択する一方で、極値関数は空テーブルに対してを返す。要件次第で何れを用いるかを検討する。
4.6 集約関数とNULL
入力が空テーブルだった場合にを返すのは集約関数も同様である。
4.7 まとめ
- は値ではない。
- 値ではないので述語も値の陽には適用できない。
- 無理やり適用するとが生じる。
- が論理演算に紛れ込むとが直観に反する動作をする。
- これらに対処すべく、段落的なステップに分けての動作を追うことが有効である。