Backend
home
1️⃣

Level1

1. 동물의 아이디와 이름

SELECT ANIMAL_ID, NAME FROM ANIMAL_INS ORDER BY ANIMAL_ID ASC;
SQL
복사

2. 어린 동물 찾기

SELECT ANIMAL_ID, NAME FROM ANIMAL_INS WHERE INTAKE_CONDITION <> 'Aged';
SQL
복사

3. 아픈 동물 찾기

-- 코드를 입력하세요 SELECT ANIMAL_ID, NAME FROM ANIMAL_INS WHERE INTAKE_CONDITION = 'Sick';
SQL
복사

4. 이름이 없는 동물의 아이디

SELECT ANIMAL_ID FROM ANIMAL_INS WHERE NAME IS NULL;
SQL
복사

5. 여러 기준으로 정렬하기

SELECT ANIMAL_ID, NAME, DATETIME FROM ANIMAL_INS ORDER BY NAME ASC, DATETIME DESC;
SQL
복사

6. 과일로 만든 아이스크림 고르기

SELECT F.FLAVOR FROM FIRST_HALF AS F JOIN ICECREAM_INFO AS I ON I.FLAVOR = F.FLAVOR WHERE F.TOTAL_ORDER > 3000 AND I.INGREDIENT_TYPE = 'fruit_based' ORDER BY F.TOTAL_ORDER DESC;
SQL
복사
JOIN 키: 두 테이블 모두 FLAVOR가 키이므로 ON F.FLAVOR = I.FLAVOR.
필터 먼저: WHERE에서 주문량과 성분 조건으로 후보를 줄이고, 그다음 ORDER BY로 정렬.
출력 컬럼: 문제 요구는 맛 이름만이므로 F.FLAVOR만 선택. (주문량은 정렬용)
SELECT F.FLAVOR FROM FIRST_HALF F WHERE F.TOTAL_ORDER > 3000 AND EXISTS( SELECT 1 FROM ICECREAM_INFO I WHERE I.FLAVOR = F.FLAVOR AND I.INGREDIENT_TYPE = 'fruit_based' ) ORDER BY F.TOTAL_ORDER DESC;
SQL
복사
인덱스가 크면 도움:
ICECREAM_INFO (INGREDIENT_TYPE, FLAVOR) 또는 (FLAVOR)
FIRST_HALF (TOTAL_ORDER, FLAVOR) 혹은 (FLAVOR, TOTAL_ORDER)
실제 데이터 분포에 따라 선택.

코드 다시 보기

AND EXISTS ( SELECT 1 FROM ICECREAM_INFO I WHERE I.FLAVOR = F.FLAVOR AND I.INGREDIENT_TYPE = 'fruit_based' )
SQL
복사

해석 과정

1.
바깥 쿼리(F)에서 한 줄씩 가져온다.
→ 즉, FIRST_HALF의 특정 맛(F.FLAVOR)을 잡고,
2.
서브쿼리 실행:
SELECT 1 FROM ICECREAM_INFO I WHERE I.FLAVOR = F.FLAVOR AND I.INGREDIENT_TYPE = 'fruit_based'
SQL
복사
ICECREAM_INFO에서 같은 맛이면서 성분이 fruit_based인 행을 찾는다.
3.
만약 그 조건을 만족하는 행이 1개라도 있다면 EXISTS(...)TRUE.
이 경우 바깥 쿼리의 F 행이 결과에 포함된다.
없다면 FALSE, 즉 제외된다.

SELECT 1은 왜 쓰는가?

EXISTS는 실제로 반환된 값에 관심 없고, 행이 존재하는지만 확인합니다.
그래서 SELECT * 대신 SELECT 1을 많이 씁니다. (관례 + 성능상 깔끔)

JOIN vs EXISTS 비교

JOIN: 두 테이블을 합쳐서 조건을 걸고 결과를 만든다.
EXISTS: 바깥 테이블 기준으로 "조건 만족하는 상대 테이블의 행이 있냐?"만 본다.
두 방법 다 답은 같지만:
EXISTS존재 여부만 확인 → 중복 걱정 없음.
JOIN조합된 행을 만들기 때문에, 조인된 결과 중복을 신경 써야 할 때가 있음.

7. 흉부외과 또는 일반외과 의사 목록 출력하기

SELECT D.DR_NAME, D.DR_ID, D.MCDP_CD, DATE_FORMAT(D.HIRE_YMD, '%Y-%m-%d') AS HIRE_YMD FROM DOCTOR AS D WHERE D.MCDP_CD IN ('CS', 'GS') ORDER BY D.HIRE_YMD DESC, D.DR_NAME ASC;
SQL
복사

8. 12세 이하인 여자 환자 목록 출력하기

SELECT P.PT_NAME, P.PT_NO, P.GEND_CD, P.AGE, IFNULL(P.TLNO, 'NONE') AS TLNO FROM PATIENT P WHERE P.AGE <= 12 AND P.GEND_CD = 'W' ORDER BY P.AGE DESC, P.PT_NAME ASC;
SQL
복사

9. 인기있는 아이스크림

SELECT F.FLAVOR FROM FIRST_HALF F ORDER BY F.TOTAL_ORDER DESC, F.SHIPMENT_ID ASC;
SQL
복사

10. 재구매가 일어난 상품과 회원 리스트 구하기

SELECT OS.USER_ID, OS.PRODUCT_ID FROM ONLINE_SALE OS GROUP BY USER_ID, PRODUCT_ID HAVING COUNT(*) >= 2 ORDER BY USER_ID ASC, PRODUCT_ID DESC;
SQL
복사
WHERE → 행 걸러내기
GROUP BY → 묶기
HAVING → 묶인 집합 걸러내기

11. 역순 정렬하기

SELECT A.NAME, A.DATETIME FROM ANIMAL_INS A ORDER BY ANIMAL_ID DESC;
SQL
복사

12. 조건에 맞는 도서 리스트 출력하기

SELECT B.BOOK_ID, DATE_FORMAT(B.PUBLISHED_DATE, "%Y-%m-%d") AS PUBLISHED_DATE FROM BOOK B WHERE B.CATEGORY = '인문' AND YEAR(PUBLISHED_DATE) = 2021 ORDER BY B.PUBLISHED_DATE ASC;
SQL
복사

13. 평균 일일 대여요금 구하기

-- 코드를 입력하세요 SELECT ROUND(AVG(DAILY_FEE), 0) AS AVERAGE_FEE FROM CAR_RENTAL_COMPANY_CAR WHERE CAR_TYPE = 'SUV';
SQL
복사

14. 강원도에 위치한 생산공장 목록 출력하기

-- 함수 적용이라 인덱스를 못 탈 수 있음. SELECT F.FACTORY_ID, F.FACTORY_NAME, F.ADDRESS FROM FOOD_FACTORY F WHERE LEFT(F.ADDRESS, 3) = '강원도' ORDER BY FACTORY_ID; -- LIKE로 해야 인덱스 적용이 가능 SELECT F.FACTORY_ID, F.FACTORY_NAME, F.ADDRESS FROM FOOD_FACTORY F WHERE ADDRESS LIKE '강원도%' ORDER BY FACTORY_ID;
SQL
복사

15. 모든 레코드 조회

SELECT * FROM ANIMAL_INS ORDER BY ANIMAL_ID;
SQL
복사

16. 상위 n개 레코드

SELECT NAME FROM ANIMAL_INS ORDER BY DATETIME ASC LIMIT 1; == 여러 명인 경우를 고려 == SELECT NAME FROM ANIMAL_INS WHERE DATETIME = (SELECT MIN(DATETIME) FROM ANIMAL_INS);
SQL
복사

17. 조건에 맞는 회원수 구하기

SELECT COUNT(*) AS USERS FROM USER_INFO WHERE LEFT(JOINED, 4) = 2021 AND AGE BETWEEN 20 AND 29; -- JOINED가 DATE 타입이라면 문자로 잘라 쓰는 대신 YEAR() 함수를 쓰는 게 더 직관적임 SELECT COUNT(*) AS USERS FROM USER_INFO WHERE YEAR(JOINED) = 2021 AND AGE BETWEEN 20 AND 29;
SQL
복사

18. 파이썬 개발자 찾기

SELECT D.ID, D.EMAIL, D.FIRST_NAME, D.LAST_NAME FROM DEVELOPER_INFOS D WHERE SKILL_1 = 'Python' OR SKILL_2 = 'Python' OR SKILL_3 = 'Python' ORDER BY D.ID;
SQL
복사

19. 잔챙이 잡은 수 구하기

SELECT COUNT(*) AS FISH_COUNT FROM FISH_INFO WHERE LENGTH IS NULL;
SQL
복사

20. 가장 큰 물고기 10마리 구하기

SELECT ID, LENGTH FROM FISH_INFO WHERE LENGTH IS NOT NULL ORDER BY LENGTH DESC, ID ASC LIMIT 10; -- 백틱 활용: 컬럼명이 함수와 같은 경우 SELECT ID, `LENGTH` FROM FISH_INFO WHERE `LENGTH` IS NOT NULL ORDER BY `LENGTH` DESC, ID ASC LIMIT 10; -- 윈도우 함수 활용 SELECT ID, `LENGTH` FROM ( SELECT ID, `LENGTH`, ROW_NUMBER() OVER (ORDER BY `LENGTH` DESC, ID ASC) AS rn FROM FISH_INFO WHERE `LENGTH` IS NOT NULL ) AS sub WHERE rn <= 10;
SQL
복사

21. 이름이 있는 동물의 아이디

SELECT ANIMAL_ID FROM ANIMAL_INS WHERE NAME IS NOT NULL ORDER BY ANIMAL_ID ASC;
SQL
복사

22. 나이 정보가 없는 회원 수 구하기

SELECT COUNT(*) AS USERS FROM USER_INFO WHERE AGE IS NULL
SQL
복사

23. 잡은 물고기의 평균 길이 구하기

SELECT ROUND(AVG(IFNULL(LENGTH, 10)), 2) AS AVERAGE_LENGTH FROM FISH_INFO;
SQL
복사

24. 가장 비싼 상품 구하기

SELECT MAX(PRICE) AS MAX_PRICE FROM PRODUCT;
SQL
복사

25. 최댓값 구하기

SELECT MAX(DATETIME) AS 시간 FROM ANIMAL_INS;
SQL
복사

26. 잡은 물고기 중 가장 큰 물고기의 길이 구하기

SELECT CONCAT(MAX(LENGTH), 'cm') AS MAX_LENGTH FROM FISH_INFO;
SQL
복사