출처
문제
DEVELOPERS 테이블에서 GRADE별 개발자의 정보를 조회하려 합니다. GRADE는 다음과 같이 정해집니다.
A : Front End 스킬과 Python 스킬을 함께 가지고 있는 개발자
B : C# 스킬을 가진 개발자
C : 그 외의 Front End 개발자
GRADE가 존재하는 개발자의 GRADE, ID, EMAIL을 조회하는 SQL 문을 작성해 주세요.
결과는 GRADE와 ID를 기준으로 오름차순 정렬해 주세요.
문제에 대한 해석
id = D162의 스킬코드는 8452
이진법으로 바꾸면 10000100000100
select conv(skill_code,10,2),skill_code,category, name
from DEVELOPERS cross join SKILLCODES
where id = 'D162'
and (skill_code&CODE)>0
cross조인을 통해 개발자가 가지고 있는 스킬을 알 수 있다
풀이(MYSQL)
-- 오답 : grade 조건에 충족하지 않은 개발자 포함됨
select 'A' as GRADE, id, email
from DEVELOPERS
where (skill_code | (select sum(code)
from SKILLCODES
where category = 'Front End')) >0
and (skill_code & (select sum(code)
from SKILLCODES
where NAME = 'Python')) >0
union all
select 'B' as GRADE, id, email
from DEVELOPERS
where (skill_code & (select sum(code)
from SKILLCODES
where NAME = 'C#')) >0
union all
select 'C' as GRADE, id, email
from DEVELOPERS
where (skill_code | (select sum(code)
from SKILLCODES
where category = 'Front End')) > 0
and not (skill_code & (select sum(code)
from SKILLCODES
where NAME = 'Python')) -- not Ture(0이 아닌 것)
and not (skill_code & (select sum(code)
from SKILLCODES
where NAME = 'C#')) -- not Ture(0이 아닌 것)
order by grade, id
그러나 D163은 grade기준에 충족되지 못함 : Front End개발자가 아님
C grade에 front end개발자중 pathon이 없는 조건을 어떻게 필터링 하는지 모르겠음..ㅠㅠ
-- 정답
SELECT
CASE WHEN EXISTS(SELECT S.CODE FROM SKILLCODES S WHERE S.CODE & D.SKILL_CODE AND S.NAME = 'Python')
AND EXISTS(SELECT S.CODE FROM SKILLCODES S WHERE S.CODE & D.SKILL_CODE AND S.CATEGORY = 'Front End') THEN 'A'
WHEN EXISTS(SELECT S.CODE FROM SKILLCODES S WHERE S.CODE & D.SKILL_CODE AND S.NAME = 'C#') THEN 'B'
WHEN EXISTS(SELECT S.CODE FROM SKILLCODES S WHERE S.CODE & D.SKILL_CODE AND S.CATEGORY = 'Front End') THEN 'C'
ELSE NULL
END AS GRADE, D.ID, D.EMAIL
FROM DEVELOPERS D
HAVING GRADE IS NOT NULL
ORDER BY GRADE, ID
작동순서
💡SQL 실행 순서는 From -> Where -> Group by -> Having -> Select -> Order by ->결과반환
- FROM 절: DEVELOPERS테이블에서
- HAVING 절: GRADE가 null값이 아닌 경우
- SELECT 절:
- SKILLCODES에서 'Python'의 이름을 가진 코드와 개발자의 코드가 일치(?) 하고 'Front End'의 카테고리 코드와 개발자의 코드가 동일한게 있는 경우 'A'
- 아니면, SKILLCODES에서'C#'의 이름을 가진 코드와 개발자의 코드가 동일한게 있는 경우 'B'
- 아니면, 'Front End'의 카테고리 코드와 개발자의 코드가 동일한게 있을 경우 'C'
- 그 외에는 null값으로 처리하고 grade라는 컬럼에 저장,
- D.ID, D.EMAIL조회
- ORDER BY 절: GRADE, ID순
배운점
- 비트연산에서 &과 | 의 차이
- case when exist의 활용
'문제풀이 > SQL(My sql)' 카테고리의 다른 글
[문제풀이] Leet code - Restaurant Growth (0) | 2024.07.10 |
---|---|
[문제풀이] Leet code - Movie Rating (0) | 2024.07.10 |
[문제풀이] 프로그래머스 - FrontEnd 개발자 찾기 (0) | 2024.07.03 |
[문제풀이] Leet code - Capital Gain/Loss (1) | 2024.07.01 |
[문제풀이] 프로그래머스 - 우유와 요거트가 담긴 장바구니 (3) | 2024.07.01 |