공부중/데이터베이스

[데이터베이스] 5주차 실습

eooonion 2026. 4. 4. 00:36

SQL 고급 실습

 

1. 

SELECT BOARD_ID, WRITER_ID, TITLE, PRICE,
    CASE
        WHEN STATUS = 'SALE' THEN '판매중'
        WHEN STATUS = 'RESERVED' THEN '예약중'
        WHEN STATUS = 'DONE' THEN '거래완료'
    END AS STATUS
FROM USED_GOODS_BOARD
WHERE CREATED_DATE = '2022-10-05'
ORDER BY BOARD_ID DESC
  • CASE문으로 STATUS의 값들을 한국어로 바꾸어준다, 이 때 칼럼 이름은 STATUS로 유지해주면 돼서 AS STATUS를 붙여준다.
  • 2022년 10월 5일에 작성된 글만 조회하는 문제이기 때문에 WHERE에서 날짜를 지정해준다.

 

2. 

SELECT  A.TITLE, A.BOARD_ID, B.REPLY_ID, B.WRITER_ID, 
        B.CONTENTS, DATE_FORMAT(B.CREATED_DATE, '%Y-%m-%d')
        AS CRAETED_DATE
 FROM  USED_GOODS_BOARD AS A
 INNER JOIN  USED_GOODS_REPLY AS B
 ON  A.BOARD_ID = B.BOARD_ID
 WHERE  SUBSTR(A.CREATED_DATE,1,7) = '2022-10'
 ORDER BY  B.CREATED_DATE ASC, A.TITLE ASC;
  • 댓글 작성일을 2022-10-05와 같은 형식으로 출력하기 위해 DATE_FORMAT을 써준다.
  • 게시글 테이블과 댓글 테이블을 합쳐야 하는 문제이기 때문에 BOARD_ID를 기준으로 조인해서 합쳐준다. INNER 조인으로 합쳤기 때문에 댓글 없는 게시글은 제외하게 된다.
  • 10월에 작성된 게시글만을 고르기 위해 SUBSTR를 이용해서 앞 7글자를 잘라내 2022-10과 같은 것만 가져온다.
    • WHERE DATE_FORMAT(A.CREATE_DATE, '%Y-%m') = '2022-10'으로 바꿔도 상관없을 것 같다.
    • 혹은 WHERE A.CREATED_DATE >= '2022-10-01'  AND A.CREATED_DATE < '2022-11-01' 이런 방법도 있다.
  • ORDER BY를 이용하여 댓글 작성일 오름차순으로 정렬해주고, 같은 날짜면 제목 기준으로 오름차순으로 정리해준다.

 

3.

SELECT b.BOOK_ID as BOOK_ID,
	a.AUTHOR_NAME as AUTHOR_NAME, 
	DATE_FORMAT(b.PUBLISHED_DATE, '%Y-%m-%d') AS PUBLISHED_DATE
FROM BOOK b
LEFT JOIN AUTHOR a ON b.AUTHOR_ID = A.AUTHOR_ID
WHERE b.CATEGORY = '경제'
ORDER BY b.PUBLISHED_DATE ASC;
  • 책 테이블과 저자 테이블을 연결해주기 위해 왼쪽 조인을 사용한다. 기준은 AUTHOR_ID
  • 왼쪽 조인을 사용하기 때문에 책은 무조건 다 나오고, 저자가 없으면 NULL로 나온다.
  • 이너 조인은 책과 저자가 둘 다 있어야 되므로 2번 문제의 이너 조인과는 차이가 있다.

 

4.

SELECT SUBSTRING(PRODUCT_CODE, 1, 2) as CATEGORY, 
       COUNT(*) as PRODUCTS
FROM PRODUCT
GROUP BY CATEGORY
ORDER BY CATEGORY
  • 카테고리를 추출하기 위해 SUBSTRING(PRODUCT_CODE, 1, 2)를 이용해 상품코드의 앞 2글자만 자른다.

 

5. 

SELECT ORDER_ID, PRODUCT_ID, DATE_FORMAT(OUT_DATE, '%Y-%m-%d') AS OUT_DATE, 
    CASE
        WHEN OUT_DATE <= '2022-05-01' THEN '출고완료'
        WHEN OUT_DATE > '2022-05-01' THEN '출고대기'
        ELSE '출고미정'
    END AS '출고여부'
FROM FOOD_ORDER
ORDER BY ORDER_ID;
  • 출고 상태를 판단하기 위해 OUT_DATE의 날짜를 비교해 출고완료와 출고대기를 나누어준다.
  • 미정이면 출고미정으로 출력해야하기 때문에 ELSE를 써준다.

 

6.

SELECT FOOD_TYPE, REST_ID, REST_NAME, FAVORITES
FROM REST_INFO
WHERE (FOOD_TYPE, FAVORITES) 
    IN (SELECT FOOD_TYPE, MAX(FAVORITES) 
        FROM REST_INFO 
        GROUP BY FOOD_TYPE)
ORDER BY FOOD_TYPE DESC
  • 현재 행의 음식종류 + 즐겨찾기 수 중에서
    • 한식의 최대 즐겨찾기, 중식의 최대 즐겨찾기, 일식의 최대 즐겨찾기를 찾는 서브쿼리 작성하여 즐겨찾기가 많은 식당만 가져오기
    • (카테고리별 1등 매장을 고르는 것)
  • IN 대신 조인을 써서 푼다면?
SELECT A.*
FROM REST_INFO A
JOIN (
    SELECT FOOD_TYPE, MAX(FAVORITES) AS MAX_FAV
    FROM REST_INFO
    GROUP BY FOOD_TYPE
) B
ON A.FOOD_TYPE = B.FOOD_TYPE 
AND A.FAVORITES = B.MAX_FAV;
  • 서브쿼리로 음식 카테고리별 최댓값을 구하고, 그 결과를 원본 테이블과 조인하여 조건에 맞는 행만 가져오는 방식으로 풀면 된다.
  • ON A.FOOD_TYPE = B.FOOD_TYPE으로 같은 음식 종류끼리 연결한다.
  • 그 중에서도 최대 즐겨찾기 값과 같은 것만 가져와야 하기 때문에 AND A.FAVORITES = B.MAX_FAV를 써준다.