프로그래머스 문제 : 자동차 대여 기록 별 대여 금액 구하기
- 문제의 설명과 예시를 꼼꼼히 파악하는 것 또한 분석의 기본 태도라고 생각하며 읽어봅시다!
![]()
* 주의사항
결과 "FEE"의 경우 예시처럼 정수부분만 출력되어야 합니다.
문제 내용
* 오늘 푼 문제 중에 가장 고민을 많이 했던 문제였던 것 같았다.
우선 '트럭'이란 car_type(자동차 종류)과 대여한 일수를 기준으로 하여 discount_rate(할인율)가 적용되는 점을 확인하고 서브쿼리를 먼저 작성하게 되었다. 해당 풀이를 먼저 확인하고 개별로 확인해보자.풀이 코드
select distinct A.history_id, case when A.rental_date = '7일 이상' then round(A.daily_fee*A.RENTAL_DAY*0.95) when A.rental_date = '30일 이상' then round(A.daily_fee*A.RENTAL_DAY*0.92) when A.rental_date = '90일 이상' then round(A.daily_fee*A.RENTAL_DAY*0.85) else A.daily_fee*A.RENTAL_DAY end as FEE from (select C.car_id, #여기가 서브쿼리입니다. C.car_type, C.daily_fee, H.history_id, case when datediff(H.end_date, H.start_date) between 7 and 29 then '7일 이상' when datediff(H.end_date, H.start_date) between 30 and 89 then '30일 이상' when datediff(H.end_date, H.start_date) >= 90 then '90일 이상' else 1 end as RENTAL_DATE, datediff(H.end_date, H.start_date)+1 as RENTAL_DAY from CAR_RENTAL_COMPANY_RENTAL_HISTORY H left join CAR_RENTAL_COMPANY_CAR C on H.car_id = C.car_id where C.car_type = '트럭') A # 여기가 서브쿼리 끝입니다. join (select * from CAR_RENTAL_COMPANY_DISCOUNT_PLAN where car_type = '트럭') P on A.car_type = P.car_type order by 2 desc, 1 desc
서브쿼리
- from 절에 필요한 요소들을 먼저 필터링하여 테이블을 조정해준다.
(select C.car_id, # 활용할 컬럼들을 지정 C.car_type, C.daily_fee, H.history_id, case when datediff(H.end_date, H.start_date) between 7 and 29 then '7일 이상' when datediff(H.end_date, H.start_date) between 30 and 89 then '30일 이상' when datediff(H.end_date, H.start_date) >= 90 then '90일 이상' else 1 end as RENTAL_DATE, # case when 을 활용하여 대여 끝날과 시작날의 차이를 계산하여 discount될 기준을 지정해줬습니다. case 해당되는 않는 값들은 1로 지정하였습니다. datediff(H.end_date, H.start_date)+1 as RENTAL_DAY # 실제로 대여 날짜를 확인하기 위해 대여 끝날과 시작날의 차이에다가 +1를 하여 대여 시작한 날짜를 포함하게 했습니다. from CAR_RENTAL_COMPANY_RENTAL_HISTORY H # 대여기록 테이블에서 ~ left join CAR_RENTAL_COMPANY_CAR C on H.car_id = C.car_id # 차의 정보가 있는 테이블에서 car_id를 기준으로 조인 where C.car_type = '트럭') A # 문제의 조건이였던 '트럭'만 가져오기 위한 조건문
From절에서 위의 서브쿼리와 조인
# DISCOUNT 정보가 담겨있는 테이블에서도 '트럭'의 정보만 가져오기 위해 조건을 주었습니다. 매칭할 수 있는 car_type으로 매칭 join (select * from CAR_RENTAL_COMPANY_DISCOUNT_PLAN where car_type = '트럭') P on A.car_type = P.car_type
SELECT 절
# 정답에서 요구한 HISTORY_ID와 대여날짜별 discount(할인율)를 적용한 비용 지정 # 서브쿼리에서 만들어준 RENTAL_DATE를 이용하여 특정 값들에 해당하는 할인율을 case when으로 개별 적용 # 7일 이상: 5% 할인 # 30일 이상: 8% 할인 # 90일 이상: 15% 할인 # 그외 7일 미만은 대여 가격과 일수만 계산 select distinct A.history_id, # distinct로 중복값이 없어진다. case when A.rental_date = '7일 이상' then round(A.daily_fee*A.RENTAL_DAY*0.95) when A.rental_date = '30일 이상' then round(A.daily_fee*A.RENTAL_DAY*0.92) when A.rental_date = '90일 이상' then round(A.daily_fee*A.RENTAL_DAY*0.85) else A.daily_fee*A.RENTAL_DAY end as FEE
ORDER BY절
# FEE컬럼을 내림차순 -> history_i컬럼을 내림차순 order by 2 desc, 1 desc
문제풀이 소감
처음에 문제만 보고 생각보다 단순하다고 생각했으나 순간 쿼리를 어떻게 나눠 짜야하나 고민했고 찾아보기도 하면서 풀었다. 더 쉬운 방법도 있긴 할테지만 현시점에선 내가 생각한 방법으로 풀어나가는 것이 중요할 것 같았다.
between 은 앞의 숫자는 이상이고 뒤에 숫자는 미만이란 것을 확인했고, select문에서 정해진 할인율은 퍼센트를 만들어서 계산하는 것보다 딱 지정을 해놓는 것이 낫겠다고 판단했다.
문제안에서 주어진 조건들을 하나씩 풀어서 정리하고 시작하여야 복잡하게 수렁으로 빠지지않은 팁이다.