본문 바로가기
C.W.K.
Stream
Lesson 05 of 10 · published

NULL과 NOT NULL

~12 min · schema, null

Level 0스키마 새싹
0 XP0/86 lessons0/10 achievements
0/120 XP to next level120 XP to go0% complete

NULL은 0도 빈 문자열도 false도 아니야

NULL은 값이 없거나 아직 모른다는 별도 상태야. 5가 아니며 0도 아니고, 입력하지 않은 문자열을 뜻하지도 않아. 따라서 5 + NULL'hi' || NULL의 결과도 NULL이 돼.

비교에는 세 번째 결과가 생겨

NULL = NULL은 참이 아니라 알 수 없음이야. 그래서 IS NULLIS NOT NULL을 써야 하고 = NULL로 찾으면 안 돼. 이 세 값 논리는 WHERE에서 조용히 행을 제외할 수 있으므로 스키마에서부터 NULL의 뜻을 좁혀야 해.

기본은 NOT NULL

반드시 있어야 하는 값이라면 NOT NULL로 선언해. 예를 들어 평점이 0인지, 5인지, 아직 매기지 않았는지는 서로 다른 상태야. 평균 같은 집계가 NULL을 건너뛴다는 점도 기억해야 해. 의미 있는 “모름”이 필요할 때만 빈자리를 허용해.

NULL까지 포함해 비교하려면

IS DISTINCT FROMIS NOT DISTINCT FROM은 NULL을 보통 값처럼 다뤄. 후자는 NULL = NULL을 TRUE로 판단해. 하위 질의에 NULL이 섞일 수 있는 WHERE id NOT IN (SELECT id FROM other) 대신 NOT EXISTS를 쓰면 예상 밖의 3값 논리를 피할 수 있어.

Code

스키마 차원에서 NULL 다루기·sql
CREATE TABLE contacts (
    id    INTEGER GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
    name  TEXT NOT NULL,           -- 항상 필수
    phone TEXT,                    -- 의도적 선택
    bio   TEXT NOT NULL DEFAULT '' -- 항상 존재, default 빈 문자열
);
WHERE의 NULL 함정·sql
-- 틀림: 아무것도 안 매치 (NULL = NULL 은 NULL, TRUE 아님)
SELECT * FROM contacts WHERE phone = NULL;

-- 맞음
SELECT * FROM contacts WHERE phone IS NULL;
SELECT * FROM contacts WHERE phone IS NOT NULL;

-- NULL-safe equality
SELECT * FROM contacts WHERE phone IS NOT DISTINCT FROM '555-1212';
집계 함수가 NULL을 건너뛰는 모습·sql
SELECT
    COUNT(*)         AS total_rows,
    COUNT(phone)     AS rows_with_phone,
    COUNT(DISTINCT phone) AS distinct_phones
FROM contacts;
-- COUNT(*) 모든 행 (NULL 포함).
-- COUNT(column) non-NULL 만.

External links

Exercise

프로젝트에서 NULL을 허용하지만 실제로는 값이 꼭 있어야 하는 열을 찾아. 기존 NULL을 먼저 채운 뒤 NOT NULL을 추가하는 마이그레이션을 설계하고, 그 열에서 NULL이 사라질 때 영향을 받는 코드를 확인해.

Progress

Progress is local-only — sign in to sync across devices.
이 페이지에서 버그를 발견하셨거나 피드백이 있으세요?문제 신고

댓글 0

🔔 답글 알림 (로그인 필요)
로그인댓글을 남기려면 로그인해 주세요.

아직 댓글이 없어요. 첫 댓글을 남겨보세요.