sql, mysql의 exists 사용하기(in과 join을 대신하자)

exsist

  • where의 서브쿼리로만 사용 가능하다. 해당 서브쿼리의 결과로서 레코드가 하나라도 있을 경우 true를 반환한다. 그러므로 서브쿼리의 select 절은 의미가 없는 값(1)을 결과로 리턴한다.
  • 레코드의 존재유무만 따지므로 대체로 IN과 JOIN보다 성능이 좋다.
CREATE TABLE students (
  id INTEGER PRIMARY KEY,
  name TEXT NOT NULL,
  gender TEXT NOT NULL
);

INSERT INTO students VALUES (1, 'Ryan', 'M');
INSERT INTO students VALUES (2, 'Joanna', 'F');

create table gender (
  gender varchar(1) primary key
);

insert into gender values('F'), ('M'), ('N');
  • 위에는 students와 gender 두 개의 테이블이 존재한다. 우리는 gender 테이블의 레코드를 출력할 예정이며, 그 조건은 students.gender에 존재하는 enum이다.
  • 먼저, exists가 없을 때를 가정하고 쿼리를 작성하면, 아래와 같이 in과 join을 사용할 수 있다.
-- exists가 없을 경우, in
select g.gender
from gender g
where g.gender in (select s.gender from students s);

-- exists가 없을 경우, join
select distinct g.gender
from gender g
join students s on g.gender = s.gender
gender
M
F
  • 만약 exists를 사용하면 다음과 같이 쿼리를 작성할 수 있다.
select g.*
from gender g
where exists(select 1 from students s where g.gender = s.gender);
  • not in 과 동일하게 not exists를 사용할 수 있으며 쿼리와 결과는 아래와 같다.
select g.*
from gender g
where not exists(select 1 from students s where g.gender = s.gender);
gender
N