상위 문서: SQL
개요
Subquery란, 다른 쿼리 안에 포함된 select-from-where 쿼리를 의미한다. 예를 들면 아래와 같다.
select name
from instructor
where dept_name = (select dept_name from department where building = 'Watson');
일반적인 SQL의 쿼리는 다음과 같은 형태를 가진다.
select A1, A2, ..., An
from r1, r2, ..., rm
where P
이때, subquery는 select, from, where 절에서 사용될 수 있다.
From 절에서의 Subquery
ri 자리에 하나의 서브쿼리를 넣을 수 있으며, 마치 테이블처럼 다룰 수 있다. 이때 subquery에는 as 키워드를 사용하여 별칭 주는 것이 일반적이다. 이는 아래와 같이 사용된다.
select *
from (select * from instructor where salary > 50000) as high_paid;
Where 절에서의 Subquery
P 자리에 조건식을 쓸 수 있는데, 그 조건식 안에 서브쿼리를 넣을 수 있다. 이때 조건식은 다음과 같이 작성된다.
B <operation> (subquery)
이때 B는 속성에 해당하며, <operation>은 비교 연산 (=, >, <, in, exists 등)에 해당한다. 이를 바탕으로 where 절에서 subquery는 아래와 같이 사용된다.
select name
from instructor
where salary > (select avg(salary) from instructor);
Select 절에서의 Subquery
Ai 자리에 단일 값을 반환하는 서브쿼리를 넣을 수 있다. 이는 아래와 같이 사용된다.
select name, (select count(*) from teaches where teaches.ID = instructor.ID) as um_courses
from instructor;
Set Membership
SQL은 튜플(값)이 어떤 relation(또는 집합)에 속하는지 여부를 검사하는 기능인 집합 멤버십(set membership)을 제공한다. in 연결자는 집합 멤버십을 테스트하는데 사용되며, 이 집합은 select 절이 생성한 값들의 모음이다. not in 연결자는 집합에 속하지 않음을 테스트하는 데 사용된다. 예를 들어, “2017년 가을 학기와 2018년 봄 학기 두 학기 모두에 개설된 과목들을 찾아라.”과 같은 쿼리를 두 집합의 교집합을 이용해 작성하였다. 하지만 이와는 in 연결자를 사용하는 방식으로도 같은 질의를 표현할 수 있다. 즉, 2017년 가을 학기에 개설된 과목 중, 2018년 봄 학기에 개설된 과목들의 집합에 속하는 과목들만 찾는 방식이다. 이는 다음과 같이 나타내어진다.
select distinct course_id
from section
where semester = 'Fall' and year = 2017 and
course_id in (select course_id
from section
where semester = 'Spring' and year = 2018);
이때 intersect 연산은 기본적으로 중복을 제거하므로, 동일한 결과를 얻기 위해 이 질의에서도 distinct를 사용해야 한다.