[성동2기 전Z전능 데이터 분석가] DAY 38
집계와 서브쿼리
함수 | 기능 | 예시 | 기능 |
서브쿼리(select) | 하부의 부수적인 질문 | select * from (select * from 테이블) 별명 |
내부 계산 |
[NOT] EXISTS (SELECT 명령) |
상관 서브쿼리 다른 테이블 상황 판단 가능 |
update 테이블 set a="있음" whrer exists (select * from sample552 where no2=no) |
no2와 no가 일치하는 것을 대상으로 a를 '있음'이라고 업데이트 |
IN | 집합 안의 값이 존재하는지 조사 가능 |
열 IN (집합) | 집합과 열을 비교 |
서브쿼리
- 다른 테이블의 값을 기준으로 한 테이블에서 데이터를 검색할 수 있도록 다른 쿼리 내부에 중첩된 쿼리
- 보통 다른 쿼리 내부에 포함되어 있는 SELECT문을 의미한다
- 용도: 데이터 필터링, 정렬, 그룹화 등
- 외부쿼리 / 내부쿼리
서브쿼리의 장점
- 파생테이블로 사용해서 더 큰 쿼리에서 다른 테이블과 조인
- 집계 함수를 계산하거나 데이터 하위 집합에 대한 다른 계산 수행
- 다른 쿼리에서 데이터 가져와서 비교
간단히 말하자면 순서 때문에 꼬인 식을 풀어주거나
다른 쿼리에서 정보를 가져와서 비교할 수 있다.
SELECT가 어떤 값을 반환하는지가 중요
- 하나의 값을 반환
- 복수의 행이 반환 열은 하나
- 하나의 행이 반환 열은 복수
- 복수의 행, 복수의 열이 반환
WHERE | 스칼라값으로 자주 사용됨 (왜냐하면 WHERE이 가장 먼저 실행되기 때문에) |
SET | 다른 테이블의 데이터를 기반으로 업데이트할 때 자주 쓰임 |
SELECT | 전체 데이터셋과 각 행을 비교할 때 자주 쓰임 |
FROM | 복잡한 집계나 조인 결과를 임시 테이블처럼 사용할 때 자주 쓰임 |
파생변수 내부쿼리에서 만들어놓으면, 외부쿼리에서 바로 사용이 가능하다!
상관 서브쿼리
EXISTS를 조합하여 서브쿼리가 반환하는 결과값이 있는지 조사할 수 있음
EXISTS : 일치하는 행이 존재하는 경우
update sample551 set a="있음" where exists(
select * from sample552 where no2=no)
NOT EXISTS : 일치하는 행이 존재하지 않는 경우
update sample551 set a="없음" where not exists(
select * from sample552 where no2=no);
열 이름이 같을 수도 있기 때문에 2개 이상의 테이블을 사용할 때는
열 이름 앞에 테이블 이름을 붙여주는 것이 좋다
elect * from sample551 where
not exists(select * from sample552 where sample552.no2 = sample551.no);
다른 테이블의 상황을 판단하고 UPDATE로 갱신, 또는 SELECT, DELETE 명령으로도 이용 가능
IN
집합과 열을 비교한다
select * from 테이블 where no in (3,5)
->3과 5를 테이블과 비교
IN에서는 집합 안에 NULL값이 있어도 무시하지 않는다.
다만 NULL=NULL을 제대로 계산할 수 없기 때문에
IN을 사용해도 NULL값은 비교할 수 없다
따라서, IS NULL을 사용해야함
NOT IN의 경우, 집합 안에 NULL이 있으면 참을 반환하지 않음( UNKNOWN이 된다!)
연습문제
-- track 테이블을 사용하여 다음 정보를 조회하는 쿼리를 작성하세요:
-- 각 아티스트의 ID (Composer 컬럼 사용)
-- 각 아티스트가 작곡한 트랙의 수
-- 각 아티스트의 트랙들의 총 재생 시간 (분 단위로 변환)
-- 각 아티스트의 트랙들의 총 가격트랙 수가 5개 이상이고,
-- 총 재생 시간이 30분을 초과하는 아티스트만 조회
-- 결과를 트랙 수가 많은 순서대로 정렬
select * from track t ;
select composer as ID,
count(*) as trackcount,
sum(Milliseconds)/60000 as playtime,
sum(UnitPrice)
from track
where composer is not null
group by composer
having count(TrackId) >=5 and sum(Milliseconds)/60000 >30
order by trackcount desc;
복수의 테이블
함수 | 기능 | 예시 | 설명 |
UNION(합집합) |
위아래로 결합 데이터가 추가되는 형식 |
SELECT * FROM A UNION SELECT * FROM B; |
A와 B를 위아래로 결합 |
UNION ALL (중복 제거 원하지 않으면) |
|||
JOIN(결합) - INNER JOIN - LEFT/RIGHT JOIN |
옆으로 결합 Coulmn이 추가되는 형식 |
내부결합과 외부결합으로 나뉜다. | |
내부결합 서로 중복되는 값만 나타남 |
SELECT FROM INNER JOIN SELECT FROM ; |
두 테이블에 모두 존재하는 행에 대해서만 출력 |
|
외부결합 하나는 모든 행을, 다른쪽은 일치되는 행만을 |
SELECT FROM LEFT/RIGHT JOIN SELECT FROM ; |
한 테이블에서 전체를, 다른 테이블에서는 교집합을 |
UNION
합치는 열의 이름이 다를 수도 있기 때문에 별명을 붙이는 것이 일반적이다.
select a as c from sample71_a
union all
select b as c from sample71_b order by c;
UNION에는 DISTINCT가 기본적으로 포함되어 있다(중복제거한다는 말)
만약 중복을 제거하고 싶지 않다면 UNION ALL을 사용한다.
JOIN
INNER JOIN
LEFT JOIN / RIGHT JOIN
한쪽 테이블에서는 모든 행을, 다른 테이블에서는 일치되는 행만 반환
(다른 테이블에서는 교집합만 반환한다고 보면 된다)
오늘의 실수
테이블을 잘못 참조해서 이상한 답이 나왔다.
쿼리문을 작성하기 전에는 잊지말고 테이블들과 열을 전부 확인하자.