데이터베이스 용어 사전
관계 모델3값 논리 · IS NULL · COALESCE

NULL

값이 '모름'임을 나타내는 세 번째 진리값. 비교·집계·유니크 제약이 전부 직관과 다르게 동작한다.

"값이 없다"가 아니라 **"모른다"**를 뜻하는 표식. SQL이 참·거짓에 더해 3값 논리를 쓰는 이유다.

비교하면 참도 거짓도 아니다

SELECT NULL = NULL;      -- NULL   (true 가 아니다)
SELECT NULL <> 1;        -- NULL
SELECT NULL > 0;         -- NULL

-- 그래서 비교 연산자로는 절대 찾을 수 없다
SELECT * FROM member WHERE phone = NULL;     -- ❌ 항상 0건
SELECT * FROM member WHERE phone IS NULL;    -- ✅ 전용 연산자를 쓴다

"모르는 값"과 "모르는 값"이 같은지도 모른다 — 이 한 줄이 아래 모든 기이함의 원인이다.

WHERE는 참인 행만 통과시킨다

-- status 가 'X' 가 아닌 행을 모두 원했는데
SELECT * FROM orders WHERE status <> 'X';
-- status 가 NULL 인 행은 빠진다 (NULL <> 'X' 는 NULL 이라 통과 못 한다)

-- 의도대로 하려면
SELECT * FROM orders WHERE status IS DISTINCT FROM 'X';        -- PostgreSQL
SELECT * FROM orders WHERE NOT (status <=> 'X');               -- MySQL (NULL-safe 비교)

집계 함수는 NULL을 건너뛴다

-- 값: 10, 20, NULL
SELECT count(*), count(amount), sum(amount), avg(amount) FROM t;
--      3          2              30           15
--                 ^ NULL 제외    ^ 제외        ^ 30/2 이지 30/3 이 아니다

avg가 예상과 다른 값을 내는 대표적 원인이다. NULL을 0으로 치려면 명시해야 한다.

SELECT avg(COALESCE(amount, 0)) FROM t;   -- 10  (30/3)

UNIQUE 제약은 NULL을 여러 개 허용한다

CREATE TABLE t (email VARCHAR(255) UNIQUE);
INSERT INTO t VALUES (NULL), (NULL), (NULL);   -- 전부 성공한다

NULL끼리는 같은지 모르므로 중복 판정이 불가능하다. "이메일은 선택 입력이지만 넣으면 유일해야 한다"가 자연스럽게 표현되는 셈이다.

-- PostgreSQL 15+ 는 NULL 도 중복으로 볼지 고를 수 있다
CREATE TABLE t (email VARCHAR(255) UNIQUE NULLS NOT DISTINCT);  -- NULL 은 하나만

정렬에서의 위치도 엔진마다 다르다

-- PostgreSQL: ASC 면 NULL 이 마지막, DESC 면 처음 (기본)
SELECT * FROM t ORDER BY amount ASC NULLS FIRST;   -- 명시할 수 있다

-- MySQL: ASC 면 NULL 이 처음 (반대다!) · NULLS FIRST 문법이 없어 우회한다
SELECT * FROM t ORDER BY amount IS NULL, amount ASC;

같은 쿼리가 두 엔진에서 다른 순서를 낸다 — 이식할 때 조용히 깨지는 지점이다.

실무 원칙

  • ① 가능하면 NOT NULL + DEFAULT 로 애초에 NULL 을 안 만든다
  • ② "값이 없음" 과 "0" · "빈 문자열" 을 구분해야 할 때만 NULL 을 쓴다
  • ③ 조인 키에는 절대 NULL 을 두지 않는다 (조인이 조용히 행을 버린다)

면접 함정

  • "NULL은 빈 값이다" → 빈 문자열 ''과 NULL은 다르다. Oracle만 예외적으로 둘을 같게 다룬다.
  • "count(*)와 count(칼럼)은 같다" → 후자는 NULL을 세지 않는다.

함께 보면 좋은 용어

노트에서 맥락과 함께 보기 — 관계 모델 — 왜 테이블인가·키·무결성·집합대수