CodeGym /행동 /SQL SELF /GREATEST()랑 LEAST() 함수 그리고 NULL

GREATEST()랑 LEAST() 함수 그리고 NULL

SQL SELF
레벨 10 , 레슨 2
사용 가능

오늘은 좀 더 특이하지만 중요한 주제로 들어가 볼게. 바로 GREATEST()LEAST() 함수야. 여러 컬럼에서 최대값, 최소값을 어떻게 찾는지, 그리고 NULL이 이 함수들에 어떤 영향을 주는지 알게 될 거야.

혹시 인생에서 제일 중요한 걸 찾아본 적 있지? (사랑, 꿈의 직장, 아니면 최고의 피자 레시피 같은 거!) 그럼 GREATEST()LEAST() 함수가 왜 필요한지 바로 감이 올 거야. 이 함수들은 어떤 것들 중에서 제일 크거나 작은 값을 찾아주는 거야. 피자 대신 숫자, 날짜, 문자열, 그리고 PostgreSQL의 다른 데이터랑 놀아주는 거지.

GREATEST()

GREATEST()는 넘겨준 값들 중에서 제일 큰 값을 돌려줘.

문법:

GREATEST(value1, value2, ..., valueN)

LEAST()

LEAST()는 반대로 제일 작은 값을 찾아줘.

문법:

LEAST(value1, value2, ..., valueN)

예시:

예를 들어 students_scores라는 테이블이 있고, 거기엔 학생들의 세 번 시험 점수가 저장돼 있다고 해보자:

student_id exam_1 exam_2 exam_3
1 85 90 82
2 NULL 76 89
3 94 NULL 88

GREATEST()LEAST()를 써보면:

SELECT
    student_id,
    GREATEST(exam_1, exam_2, exam_3) AS highest_score,
    LEAST(exam_1, exam_2, exam_3) AS lowest_score
FROM students_scores;

결과:

student_id highest_score lowest_score
1 90 82
2 89 NULL
3 94 NULL

NULLGREATEST()LEAST()에 미치는 영향

이제 진짜 재밌는 부분이야. 테이블 값들 중에 NULL도 있을 수 있잖아. 이미 알다시피 NULL은 데이터가 없거나 모르는 값을 뜻하는 신비한 존재야. 그럼 NULL이 PostgreSQL에서 GREATEST()LEAST()에 들어가면 어떻게 되는지 보자.

NULL의 동작:

PostgreSQL에서 GREATEST()LEAST() 함수는 좀 특별하게 동작해. 이 함수들은 NULL 값을 무시하고, 인자 중에서 제일 크거나 작은 값을 찾아줘. 중요: 단, 모든 인자가 NULL이면 결과도 NULL이야.

예시:

SELECT
    GREATEST(10, 20, NULL, 5) AS greatest_value,
    LEAST(10, 20, NULL, 5) AS least_value;

결과:

greatest_value least_value
20 5

보다시피 NULL은 무시되고, 함수는 남아있는 값들(10, 20, 5) 중에서 최대/최소를 돌려줘.

이번엔 모든 인자가 NULL일 때 예시:

예시:

SELECT
    GREATEST(NULL, NULL) AS greatest_nulls,
    LEAST(NULL, NULL) AS least_nulls;

결과:

greatest_nulls least_nulls
NULL NULL

NULL 문제를 어떻게 피할까?

PostgreSQL은 기본적으로 NULL을 무시하지만, 가끔은 다른 동작이 필요할 수도 있어. 예를 들어, NULL을 0이나 다른 기본값으로 간주해서 최대/최소를 구하고 싶을 때가 있지. 이럴 땐 COALESCE() 함수를 쓰면 돼.

COALESCE(arg1, arg2, ...) 함수는 인자 중에서 첫 번째로 NULL이 아닌 값을 돌려줘. 이걸로 GREATEST()LEAST()에 넘기기 전에 NULL을 원하는 값으로 바꿀 수 있어.

예시 1: NULL을 0으로 바꾸기

예를 들어, 점수가 NULL이면 0점으로 간주하고 싶다고 해보자. COALESCE()로 기본값을 넣어줄 수 있어.

원본 테이블은 이래:

student_id exam_1 exam_2 exam_3
1 90 85 82
2 NULL 89 NULL
3 NULL NULL 94

쿼리:

SELECT
    student_id,
    GREATEST(
        COALESCE(exam_1, 0), 
        COALESCE(exam_2, 0), 
        COALESCE(exam_3, 0)
    ) AS highest_score,
    LEAST(
        COALESCE(exam_1, 0), 
        COALESCE(exam_2, 0), 
        COALESCE(exam_3, 0)
    ) AS lowest_score
FROM students_scores;

결과:

student_id highest_score lowest_score
1 90 82
2 89 0
3 94 0

예시 2: NULL을 다른 컬럼 값으로 바꾸기

가끔은 0 같은 고정값 대신, 다른 컬럼 값을 넣고 싶을 때도 있어. 예를 들어 exam_3이 없으면 exam_1 값을 대신 쓰고 싶을 때!

SELECT
    student_id,
    GREATEST(
        exam_1, 
        exam_2, 
        COALESCE(exam_3, exam_1)
    ) AS highest_score
FROM students_scores;

테이블이 이렇게 있다고 해보자:

student_id exam_1 exam_2 exam_3
1 90 85 82
2 NULL 89 NULL
3 70 NULL NULL

쿼리 결과:

student_id highest_score
1 90
2 89
3 70

실전 케이스

케이스 1: 최대 할인 찾기

order_id discount_1 discount_2 discount_3
101 5 10 7
102 NULL 3 8
103 15 NULL NULL
104 NULL NULL NULL

orders 테이블에서 각 주문마다 세 가지 할인 타입이 있을 수 있어. 각 주문별로 최대 할인을 찾아야 해.

SELECT
    order_id,
    GREATEST(discount_1, discount_2, discount_3) AS max_discount
FROM orders;

결과:

order_id max_discount
101 10
102 8
103 15
104 NULL

케이스 2: 상품의 최소 가격 찾기

products 테이블에는 상품 가격이 USD, EUR, GBP 세 통화로 저장돼 있어. 각 상품별로 최소 가격을 찾아야 해.

product_id price_usd price_eur price_gbp
1 100 95 80
2 NULL 150 140
3 200 NULL NULL
4 NULL NULL NULL
SELECT
    product_id,
    LEAST(price_usd, price_eur, price_gbp) AS lowest_price
FROM products;
product_id lowest_price
1 80
2 140
3 200
4 NULL

모든 가격이 NULL이면 결과도 NULL이야

GREATEST()LEAST() 쓸 때 흔한 실수

실수 1: NULL 때문에 예상치 못한 결과.

강의 앞부분에서 NULL이 PostgreSQL에서 GREATEST()LEAST()에 어떻게 영향을 주는지 자세히 봤지. 가장 흔한 실수는, 다른 DBMS에서 NULL이 하나라도 있으면 결과가 전부 NULL이 되는 걸 기대하는 거야. PostgreSQL은 다르거든.

실수 예시: 인자 중에 NULL이 있으면 함수가 항상 NULL을 돌려줄 거라고 착각할 수 있어. 그래서 쓸데없이 모든 인자에 COALESCE()를 써서 쿼리가 복잡해지고 느려질 수도 있어. 사실 NULL은 그냥 무시해도 되는 상황이 많아.

실수 2: GREATEST()LEAST()를 타입이 안 맞는 값에 쓰기.

GREATEST()LEAST() 함수는 같은 데이터 타입이거나 서로 자동 변환 가능한 타입끼리만 비교할 수 있어. 완전히 다른 타입을 비교하려고 하면 에러가 나.

실수 예시: 데이터 타입이 안 맞는다는 에러 메시지를 받게 될 거야.

코멘트
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION