[TIL] #7. 프로그래머스 JOIN

[ JOIN ]

테이블 사이의 복잡한 관계를 파악해보아요.

🔗 JOIN 개념과 기본 코드는 여기 참고하기


[ 없어진 기록 찾기 ]

🔗 문제 바로가기

문제 정리

1. 테이블 정리

  • ANIMAL_INS: 동물 보호소에 들어온 동물의 정보를 담은 테이블
  • ANIMAL_OUTS: 동물 보호소에 입양 보낸 동물의 정보를 담은 테이블

2. 필드 정보

  • ANIMAL_ID: 동물의 아이디
  • ANIMAL_TYPE: 생물 종
  • DATETIME
    • ANIMAL_INS → 보호 시작일
    • ANIMAL_OUTS → 입양일
  • INTAKE_CONDITION: 보호 시작 시 상태
  • NAME: 이름
  • 성별 및 중성화 여부
    • ANIMAL_INSSEX_UPON_INTAKE
    • ANIMAL_OUTSSEX_UPON_OUTCOME

ANIMAL_OUTS 테이블의 ANIMAL_IDANIMAL_INSANIMAL_ID의 외래 키이다.

3. 문제

일부 데이터가 유실되어 입양을 간 기록은 있는데, 보호소에 들어온 기록이 없는 동물의 ID와 이름을 ID순으로 조회하는 SQL문을 작성하라.

  • DATETIME 정보가 ANIMAL_OUTS에만 있는 레코드를 원한다.
    → 이렇게 정보가 한쪽 테이블에만 있을 경우, LEFT JOIN을 이용해야 한다.
    (RIGHT JOIN도 당연히 가능!)
  • ANIMAL_OUTSANIMAL_IDANIMAL_INSANIMAL_ID가 같은 것을 기준으로 JOIN 해야한다.
  • ANIMAL_INS에도 DATETIME 정보가 있으므로 ANIMAL_INSDATETIME 정보가 없는 것을 가져오기 위해서는 NULL인 값만 가져와야 한다는 조건을 추가해야 한다.
  • ANIMAL_ID순으로 조회해야 한다.

풀이

✅ 코드 분석

SELECT ANIMAL_OUTS.ANIMAL_ID, ANIMAL_OUTS.NAME
  • ANIMAL_IDNAME 필드값을 조회한다.

FROM ANIMAL_OUTS
LEFT JOIN ANIMAL_INS
ON ANIMAL_OUTS.ANIMAL_ID = ANIMAL_INS.ANIMAL_ID
  • LEFT JOIN을 이용하여 ANIMAL_OUTS 테이블을 기준으로 ANIMAL_INS 테이블을 조합한다.
  • ANIMAL_OUTS.ANIMAL_IDANIMAL_INS.ANIMAL_ID가 같은 값만 가져온다.

WHERE ANIMAL_INS.DATETIME IS NULL
  • ANIMAL_INS.DATETIME 정보가 없는, 즉 NULL인 값만 가져온다.

ORDER BY ANIMAL_OUTS.ANIMAL_ID
  • ANIMAL_OUTS.ANIMAL_ID 필드값을 기준으로 오름차순으로 정렬한다.

✅ 전체 코드

SELECT ANIMAL_OUTS.ANIMAL_ID, ANIMAL_OUTS.NAME
FROM ANIMAL_OUTS
LEFT JOIN ANIMAL_INS
ON ANIMAL_OUTS.ANIMAL_ID = ANIMAL_INS.ANIMAL_ID
WHERE ANIMAL_INS.DATETIME IS NULL
ORDER BY ANIMAL_OUTS.ANIMAL_ID

[ 있었는데요 없었습니다 ]

🔗 문제 바로가기

문제 정리

1. 테이블 정리

  • ANIMAL_INS: 동물 보호소에 들어온 동물의 정보를 담은 테이블
  • ANIMAL_OUTS: 동물 보호소에 입양 보낸 동물의 정보를 담은 테이블

2. 필드 정보

  • ANIMAL_ID: 동물의 아이디
  • ANIMAL_TYPE: 생물 종
  • DATETIME
    • ANIMAL_INS → 보호 시작일
    • ANIMAL_OUTS → 입양일
  • INTAKE_CONDITION: 보호 시작 시 상태
  • NAME: 이름
  • 성별 및 중성화 여부
    • ANIMAL_INSSEX_UPON_INTAKE
    • ANIMAL_OUTSSEX_UPON_OUTCOME

ANIMAL_OUTS 테이블의 ANIMAL_IDANIMAL_INSANIMAL_ID의 외래 키이다.

3. 문제

관리자의 실수로 일부 동물의 입양일이 잘못 입력되었다. 보호 시작일보다 입양일이 더 빠른 동물의 아이디와 이름을 조회하는 SQL문을 작성하라. 이때 결과는 보호 시작일이 빠른 순으로 조회해야 한다.

  • ANIMAL_OUTS.DATETIME 값 중 잘못된 값이 있다. 그러므로 ANIMAL_INS.DATETIME 값을 가져와야 한다.
    → 이번에는 RIGHT JOIN 이용!
  • ANIMAL_OUTSANIMAL_IDANIMAL_INSANIMAL_ID가 같은 것을 기준으로 JOIN 해야한다.
  • ANIMAL_OUTS.DATETIME 값이 ANIMAL_INS.DATETIME 값보다 큰 레코드를 가져와야 한다.
  • ANIMAL_INS.DATETIME 값을 기준으로 오름차순으로 조회해야 한다.

풀이

✅ 코드 분석

SELECT ANIMAL_INS.ANIMAL_ID, ANIMAL_INS.NAME
  • ANIMAL_IDNAME 필드값을 조회한다.

FROM ANIMAL_OUTS
RIGHT JOIN ANIMAL_INS
ON ANIMAL_OUTS.ANIMAL_ID = ANIMAL_INS.ANIMAL_ID
  • RIGHT JOIN을 이용하여 ANIMAL_INS 테이블을 기준으로 ANIMAL_OUTS 테이블을 조합한다.
  • ANIMAL_OUTS.ANIMAL_IDANIMAL_INS.ANIMAL_ID가 값은 값만 가져온다.

WHERE ANIMAL_OUTS.DATETIME < ANIMAL_INS.DATETIME
  • ANIMAL_OUTS.DATETIME 값이 ANIMAL_INS.DATETIME보다 작은 값만 가져온다.

ORDER BY ANIMAL_INS.DATETIME
  • ANIMAL_INS.DATETIME 값을 기준으로 오름차순으로 정렬한다.

✅ 전체 코드

SELECT ANIMAL_INS.ANIMAL_ID, ANIMAL_INS.NAME
FROM ANIMAL_OUTS
RIGHT JOIN ANIMAL_INS
ON ANIMAL_OUTS.ANIMAL_ID = ANIMAL_INS.ANIMAL_ID
WHERE ANIMAL_OUTS.DATETIME < ANIMAL_INS.DATETIME
ORDER BY ANIMAL_INS.DATETIME

[ 오랜 기간 보호한 동물(1) ]

🔗 문제 바로가기

문제 정리

1. 테이블 정리

  • ANIMAL_INS: 동물 보호소에 들어온 동물의 정보를 담은 테이블
  • ANIMAL_OUTS: 동물 보호소에 입양 보낸 동물의 정보를 담은 테이블

2. 필드 정보

  • ANIMAL_ID: 동물의 아이디
  • ANIMAL_TYPE: 생물 종
  • DATETIME
    • ANIMAL_INS → 보호 시작일
    • ANIMAL_OUTS → 입양일
  • INTAKE_CONDITION: 보호 시작 시 상태
  • NAME: 이름
  • 성별 및 중성화 여부
    • ANIMAL_INSSEX_UPON_INTAKE
    • ANIMAL_OUTSSEX_UPON_OUTCOME

ANIMAL_OUTS 테이블의 ANIMAL_IDANIMAL_INSANIMAL_ID의 외래 키이다.

3. 문제

아직 입양을 못 간 동물 중, 가장 오래 보호소에 있었던 동물 3마리의 이름과 보호 시작일을 조회하는 SQL문을 작성하라. 이때 결과는 보호 시작일 순으로 조회해야 한다.

  • DATETIME 정보가 ANIMAL_INS에만 있는 레코드를 원한다.
    LEFT JOIN 이용!
  • ANIMAL_OUTSANIMAL_IDANIMAL_INSANIMAL_ID가 같은 것을 기준으로 JOIN 해야한다.
  • ANIMAL_OUTS에도 DATETIME 정보가 있으므로 ANIMAL_OUTSDATETIME 정보가 없는 것을 가져오기 위해서는 NULL인 값만 가져와야 한다는 조건을 추가해야 한다.
  • ANIMAL_INS.DATETIME 값을 기준으로 오름차순으로 조회해야 한다.

풀이

✅ 코드 분석

SELECT INS.NAME, INS.DATETIME
  • NAMEDATETIME 필드값을 조회한다.

FROM ANIMAL_INS AS INS
LEFT JOIN ANIMAL_OUTS AS OUTS
ON INS.ANIMAL_ID = OUTS.ANIMAL_ID
  • LEFT JOIN을 이용하여 ANIMAL_INS 테이블을 기준으로 ANIMAL_OUTS 테이블을 조합한다.
  • ANIMAL_OUTS.ANIMAL_IDANIMAL_INS.ANIMAL_ID가 같은 값만 가져온다.
  • AS 키워드를 이용하여 별칭을 부여하여 사용하였다.

WHERE OUTS.DATETIME IS NULL
  • OUTS.DATETIME 정보가 없는, 즉 NULL인 값만 가져온다.

ORDER BY INS.DATETIME
LIMIT 3
  • INS.DATETIME 값을 기준으로 오름차순으로 정렬한 뒤, 3개만 가져온다.

✅ 전체 코드

SELECT INS.NAME, INS.DATETIME
FROM ANIMAL_INS AS INS
LEFT JOIN ANIMAL_OUTS AS OUTS
ON INS.ANIMAL_ID = OUTS.ANIMAL_ID
WHERE OUTS.DATETIME IS NULL
ORDER BY INS.DATETIME
LIMIT 3

[ 보호소에서 중성화한 동물 ]

문제 정리

1. 테이블 정리

  • ANIMAL_INS: 동물 보호소에 들어온 동물의 정보를 담은 테이블
  • ANIMAL_OUTS: 동물 보호소에 입양 보낸 동물의 정보를 담은 테이블

2. 필드 정보

  • ANIMAL_ID: 동물의 아이디
  • ANIMAL_TYPE: 생물 종
  • DATETIME
    • ANIMAL_INS → 보호 시작일
    • ANIMAL_OUTS → 입양일
  • INTAKE_CONDITION: 보호 시작 시 상태
  • NAME: 이름
  • 성별 및 중성화 여부
    • ANIMAL_INSSEX_UPON_INTAKE
    • ANIMAL_OUTSSEX_UPON_OUTCOME

ANIMAL_OUTS 테이블의 ANIMAL_IDANIMAL_INSANIMAL_ID의 외래 키이다.

3. 문제

보호소에서 중성화 수술을 거친 동물 정보를 알아보려고 한다. 보호소에 들어올 당시에는 중성화되지 않았지만, 보호소를 나갈 당시에는 중성화된 동물의 아이디와 생물 종, 이름을 조회하는 아이디 순으로 조회하는 SQL 문을 작성하라.

  • 중성화를 거치지 않은 동물은 Intact, 중성화를 거친 동물은 Spayed 또는 Neutered라고 표시되어 있다.
  • ANIMAL_OUTS, ANIMAL_INS 테이블에 모두 있는 데이터를 가져와야 하므로 INNER JOIN을 사용한다.
  • ANIMAL_OUTSANIMAL_IDANIMAL_INSANIMAL_ID가 같은 것을 기준으로 JOIN 해야한다.
  • ANIMAL_INS.SEX_UPON_INTAKE 값은 'Intact'를 포함해야 하고, ANIMAL_OUTS.SEX_UPON_OUTCOME 값은 Spayed 또는 Neutered를 포함해야 한다.
  • ANIMAL_ID순으로 조회해야 한다.

풀이

✅ 코드 분석

SELECT INS.ANIMAL_ID, INS.ANIMAL_TYPE, INS.NAME
  • ANIMAL_IDANIMAL_TYPE, NAME 필드값을 조회한다.

FROM ANIMAL_INS AS INS
JOIN ANIMAL_OUTS AS OUTS
ON INS.ANIMAL_ID = OUTS.ANIMAL_ID
  • INNER JOIN을 이용하여 ANIMAL_INS, ANIMAL_OUTS 테이블의 공통 부분을 가져온다.
  • OUTS.ANIMAL_IDINS.ANIMAL_ID가 같은 값만 가져온다.

WHERE SEX_UPON_INTAKE LIKE "%Intact%"
	AND (SEX_UPON_OUTCOME LIKE "Spayed%"
		OR SEX_UPON_OUTCOME LIKE "Neutered%")
  • ANIMAL_INS.SEX_UPON_INTAKE 값이 "Intact"를 포함하고,
    ANIMAL_OUTS.SEX_UPON_OUTCOME 값이 "Spayed" 또는 "Neutered"를 포함하는 값만 가져온다.

위의 조건을 다른 방식으로 표현할 수 있다.

1. NOT LIKE 이용

WHERE SEX_UPON_INTAKE LIKE "%Intact%"
	AND SEX_UPON_OUTCOME NOT LIKE "%Intact%"
  • NOT LIKE을 이용하여 SEX_UPON_OUTCOME"Intact"를 포함하지 않을 경우에만 가져오면 된다.

2. SEX_UPON_INTAKE와 SEX_UPON_OUTCOME 값 이용하기

WHERE SEX_UPON_INTAKE LIKE "%Intact%"
    AND SEX_UPON_INTAKE != SEX_UPON_OUTCOME
  • 중성화를 했다면 SEX_UPON_INTAKESEX_UPON_OUTCOME의 값이 달라지므로 값이 다른 경우에만 가져오면 된다.

ORDER BY INS.ANIMAL_ID
  • ANIMAL_ID 필드값을 기준으로 오름차순으로 정렬한다.

✅ 전체 코드

SELECT INS.ANIMAL_ID, INS.ANIMAL_TYPE, INS.NAME
FROM ANIMAL_INS AS INS
JOIN ANIMAL_OUTS AS OUTS
ON INS.ANIMAL_ID = OUTS.ANIMAL_ID
WHERE SEX_UPON_INTAKE LIKE "%Intact%"
    AND SEX_UPON_INTAKE != SEX_UPON_OUTCOME
ORDER BY INS.ANIMAL_ID

좋은 웹페이지 즐겨찾기