結論としてはタイトルの通りなのだが、実際にやばみを目視で確認してみた。
NOT NULL のboolean型による真理値表
全パターン(4レコード)を持つテーブルを作成
-- 2値テーブル作成
create table truth(
condition_a boolean NOT NULL,
condition_b boolean NOT NULL
);
INSERT INTO truth (condition_a,condition_b) VALUES(TRUE,TRUE);
INSERT INTO truth (condition_a,condition_b) VALUES(TRUE,FALSE);
INSERT INTO truth (condition_a,condition_b) VALUES(FALSE,TRUE);
INSERT INTO truth (condition_a,condition_b) VALUES(FALSE,FALSE);
真理値表を取得するSQL
作成したtruthテーブルに対して、真理値表を取得するSQLを叩いてみる。
select
condition_a,
condition_b,
-- 論理積
condition_a AND condition_b as cond_and,
-- 論理和
condition_a OR condition_b as OR,
-- 排他的論理和
condition_a <> condition_b as XOR,
-- 否定排他的論理和
condition_a = condition_b as XNOR,
-- 否定論理和
NOT condition_a AND NOT condition_b as NOR,
-- 否定論理積
NOT (condition_a AND condition_b) as NAND
FROM
truth;
結果
はい。
A | B | AND | OR | XOR | XNOR | NOR | NAND | |
---|---|---|---|---|---|---|---|---|
1 | TRUE | TRUE | TRUE | TRUE | FALSE | TRUE | FALSE | FALSE |
2 | TRUE | FALSE | FALSE | TRUE | TRUE | FALSE | FALSE | TRUE |
3 | FALSE | TRUE | FALSE | TRUE | TRUE | FALSE | FALSE | TRUE |
4 | FALSE | FALSE | FALSE | FALSE | FALSE | TRUE | TRUE | TRUE |
NULLABLE なboolean型による真理値表
今度は、Nullableなboolean型の2列を持つ、3値のテーブルを作ってみる。
create table truth_with_null(
condition_a boolean ,
condition_b boolean
);
-- 全パターン
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(TRUE,TRUE);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(TRUE,FALSE);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(TRUE,NULL);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(FALSE,TRUE);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(FALSE,FALSE);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(FALSE,NULL);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(NULL,TRUE);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(NULL,FALSE);
INSERT INTO truth_with_null (condition_a,condition_b) VALUES(NULL,NULL);
同じSQLを叩いてみる。
select
condition_a,
condition_b,
-- 論理積
condition_a AND condition_b as cond_and,
-- 論理和
condition_a OR condition_b as OR,
-- 排他的論理和
condition_a <> condition_b as XOR,
-- 否定排他的論理和
condition_a = condition_b as XNOR,
-- 否定論理和
NOT condition_a AND NOT condition_b as NOR,
-- 否定論理積
NOT (condition_a AND condition_b) as NAND
FROM
truth_with_null
;
結果
やべえ
A | B | AND | OR | XOR | XNOR | NOR | NAND | |
---|---|---|---|---|---|---|---|---|
1 | TRUE | TRUE | TRUE | TRUE | FALSE | TRUE | FALSE | FALSE |
2 | TRUE | FALSE | FALSE | TRUE | TRUE | FALSE | FALSE | TRUE |
3 | TRUE | TRUE | FALSE | |||||
4 | FALSE | TRUE | FALSE | TRUE | TRUE | FALSE | FALSE | TRUE |
5 | FALSE | FALSE | FALSE | FALSE | FALSE | TRUE | TRUE | TRUE |
6 | FALSE | FALSE | TRUE | |||||
7 | TRUE | TRUE | FALSE | |||||
8 | FALSE | FALSE | TRUE | |||||
9 |
経験則として「boolean型をNullableにするな」で思考停止していたが、改めて確認してやばい動きをしているのが分かる。
(TRUE AND NULL) がNULL になり、
(FALSE AND NULL) がFALSE になるの、やばくないですか?
そして、
(TRUE OR NULL) がTRUEになり、
(FALSE OR NULL) がNULL になるのも、やばくないですか?
https://www.postgresql.jp/document/9.6/html/functions-comparison.html
https://qiita.com/kiimiiis/items/119cdbd51c588c4b1f62