[MySQL] selet 컬럼명을 조건에 따라 다르게 출력할 수 있을까?
오늘 쿼리를 작성하다가 궁금증이 생겼다.
예를 들어 학교 교직원 및 학생 정보를 user테이블에 다 있다고 생각해보자.
relation테이블을 이용하여 학생의 담임교사와 학부모정보를 출력하고 싶었다.
user테이블에서 자기 자신을 계속 join하는 상황에서 상황별 학생정보를 출력하려면 어떻게 해야할까?
첫 시도와 문제점 ☝️
1 | // 모든 정보가 다 있는 경우 |
위 쿼리의 문제점은 크게 2가지이다.
- 학부모정보가 없는 경우 학생정보가 아예 출력 안됨.
- 담임교사 정보가 없는 경우 학생정보가 아예 출력 안됨.
학무보정보나 담임교사정보가 없는 상황에서도 학생정보를 출력하고 싶다면 어떻게 해야할까?
모든 쿼리를 다 만들면 어때? 🤔
먼저 if나 case절을 생각했는데 아무래도 select값이 변경되어야하기때문에 사용하기가 힘들었다.
그렇다면 모든 경우의 수별로 쿼리를 다 만들어보는 방법이 있다.
예를 들면 아래와 같다.
- 모든 정보가 다 있는 경우
1 | // 모든 정보가 다 있는 경우 |
- 담임정보가 없는 경우
1 | // 담임정보가 없는 경우 |
- 학부모정보가 없는 경우
1 | // 학부모정보가 없는 경우 |
- 담임정보도 없고 학부모정도 없는 경우
1 | // 담임정보도 없고 학부모정도 없는 경우 |
보시다시피 너무 비효율적이다.
한 쿼리로 해결하는 방법이 없을까? 구글링하다가 도저히 모르겠어서 팀장님께 조심스럽게 물어봤는데 바로 해결방법을 알려주셨다!
한 쿼리로 해결 😎
해결책은 바로 left outer join이었다!
1 | select u1.name, u1.tel, --학생정보 |
위에서 내가 작성한 join 앞에 아무것도 적지않았으므로 기본적으로 inner조인이 된다. 즉 교집합만 보여주는 쿼리가 된다.
outer조인에는 크게 3가지가 있고 그 중 left outer join을 실무에서 가장 많이 사용한다고 한다.
아무리 쉬워보이는 거라도 용기내서 물어보길 잘했다! 덕분에 확실히 개념이 잡혔다. 룰루!
outer join이란?
아래 그림을 보면 이해하기가 쉽다.
- join = inner join : 교집합
- outer join 종류
- left outer join : 실무에서 가장 많이 사용
- right outer join
- full outer join
SQL NULL 처리하기
팀장님께서 추가로 null값이 들때 default값을 설정할 수 있는 COALESCE()도 함께 알려주셨다.