https://school.programmers.co.kr/learn/courses/30/lessons/151139
코드설명
1. 먼저 subquery 로 '2022-08-01' ~ '2022-11-01' 사이 동안에 대여기록이 5회이상인 자동차의 아이디(car_id)를 가져옵니다.
select * from car_rental_company_rental_history where start_date >= '2022-08-01' and start_date < '2022-11-01' group by car_id having count(*) >= 5
2. inner join으로 묶습니다.
SELECT MONTH(CRCRH.START_DATE) AS MONTH, CRCRH.CAR_ID, COUNT(*) AS RECORDS
FROM CAR_RENTAL_COMPANY_RENTAL_HISTORY AS CRCRH
INNER JOIN (select car_id from car_rental_company_rental_history where start_date >= '2022-08-01' and start_date < '2022-11-01' group by car_id having count(*) >= 5) AS CRCRH2
ON CRCRH.CAR_ID = CRCRH2.CAR_ID
3. inner join을 하면, 해당 '2022-08-01' ~ '2022-11-01' 사이에 5번 빌린 모두 자동차 아이디가 반환되는데,
이떄, 다시 한번 WHERE 로 날짜를 필터링해야 합니다! (이 부분에서 꽤 오랜시간 디버깅했습니다..)
SELECT MONTH(CRCRH.START_DATE) AS MONTH, CRCRH.CAR_ID, COUNT(*) AS RECORDS
FROM CAR_RENTAL_COMPANY_RENTAL_HISTORY AS CRCRH
INNER JOIN (select car_id from car_rental_company_rental_history where start_date >= '2022-08-01' and start_date < '2022-11-01' group by car_id having count(*) >= 5) AS CRCRH2
ON CRCRH.CAR_ID = CRCRH2.CAR_ID
WHERE CRCRH.START_DATE >= '2022-08-01' AND CRCRH.START_DATE < '2022-11-01'
GROUP BY MONTH(CRCRH.START_DATE), CRCRH.CAR_ID
HAVING COUNT(*) > 0
ORDER BY MONTH(CRCRH.START_DATE) ASC, CRCRH.CAR_ID DESC
여기서 이미 아래의 코드에서 8월부터 11월까지의 차들만 가져온 것 아닌가? 하는 의문이 생깁니다.
select * from car_rental_company_rental_history where start_date >= '2022-08-01' and start_date < '2022-11-01' group by car_id having count(*) >= 5
맞습니다. 하지만, 이후에 INNER JOIN 을 하면서 해당 CAR_ID가 '2022년-4월'에도 차를 렌탈한 기록이 있을 수 있습니다.
그렇게 된다면, 4월값도 같이 INNER JOIN 되므로, 마지막에 출력할떄 8월 9월 10월에 대한 정보가 나오는것이 아닌, 4월정보도 나올 수 있는 것 입니다.
그러므로 INNER JOIN 이후에도 WHERE 절로, 2022년 8월부터 2022년 10월까지 총 대여 횟수가 5회 이상인 자동차들에 대해서 """"해당 기간""" 동안의 월별 자동차 ID 별 총 대여 횟수(컬럼명: RECORDS ...
"해당 기간"을 다시 필터링해야합니다.
다른 월에도 CAR_ID 기록이 있을 수 있다는 것을 알아야하는 문제였습니다.
즉, 우리가 가져온 데이터는 오직 CAR_ID라는 것입니다.
코드
SELECT MONTH(CRCRH.START_DATE) AS MONTH, CRCRH.CAR_ID, COUNT(*) AS RECORDS
FROM CAR_RENTAL_COMPANY_RENTAL_HISTORY AS CRCRH
INNER JOIN (select car_id from car_rental_company_rental_history where start_date >= '2022-08-01' and start_date < '2022-11-01' group by car_id having count(*) >= 5) AS CRCRH2
ON CRCRH.CAR_ID = CRCRH2.CAR_ID
WHERE CRCRH.START_DATE >= '2022-08-01' AND CRCRH.START_DATE < '2022-11-01'
GROUP BY MONTH(CRCRH.START_DATE), CRCRH.CAR_ID
HAVING COUNT(*) > 0
ORDER BY MONTH(CRCRH.START_DATE) ASC, CRCRH.CAR_ID DESC
ORACLE
SELECT TO_NUMBER(TO_CHAR(CRCRH.START_DATE,'MM')), CRCRH.CAR_ID, COUNT(*)
FROM CAR_RENTAL_COMPANY_RENTAL_HISTORY CRCRH
INNER JOIN ( SELECT CAR_ID FROM CAR_RENTAL_COMPANY_RENTAL_HISTORY WHERE
START_DATE >= TO_DATE('2022-08-01','YYYY-MM-DD') AND START_DATE < TO_DATE('2022-11-01','YYYY-MM-DD')
GROUP BY CAR_ID
HAVING COUNT(*) >= 5
) CRCRH2
ON CRCRH.CAR_ID = CRCRH2.CAR_ID
WHERE CRCRH.START_DATE >= TO_DATE('2022-08-01','YYYY-MM-DD') AND CRCRH.START_DATE < TO_DATE('2022-11-01','YYYY-MM-DD')
GROUP BY TO_NUMBER(TO_CHAR(CRCRH.START_DATE,'MM')), CRCRH.CAR_ID
HAVING COUNT(*) > 0
ORDER BY TO_NUMBER(TO_CHAR(CRCRH.START_DATE,'MM')) ASC, CRCRH.CAR_ID DESC