재귀쿼리(recursive)란?
재귀함수란 함수 안에 자신의 함수를 다시 호출하는 함수이다.
재귀함수는 자신의 로직을 내부적으로 반복하다가, 일정한 조건이 만족되면 함수를 이탈하여 결과를 도출한다.
재귀쿼리(recursive) 문법
1. with문 :
- WITH RECURSIVE 문
∙ 재귀쿼리는 꼭 with문 안에 넣어줘야 한다.
∙ 일반 with문과 다르게 cte앞에 'recursive'를 적어줘야 한다 ( ex: with recursive cte as )
2. 비반복문 (Non-Recursive) select 문 :
∙재귀쿼리의 일종의 root을 만들어줘야 한다. ( i = i + 1을 반복할 때, root로 i = 1을 심어주는 것 )
3. union all
∙ root와 반복할 쿼리를 합쳐준다.
4. 반복문 (Recursive) select 문
∙ 반복할 부분을 쿼리로 작성해준다. ( ex. i = i + 1 )
∙ 반드시 정지조건을 넣어줘야한다 ! 아니면 무한루프에 빠질지도 ... ( ex. i (반복할 변수) < 25 )
프로그래머스 예제
https://school.programmers.co.kr/learn/courses/30/lessons/301651
쿼리
with recursive cte as
(select 1 as generation, id -- 비반복문 (root)
from ecoli_data
where parent_id is null
union all -- 비반복문과 반복문을 union해준다
select generation + 1, b.id -- 반복문
from cte a
join ecoli_data b
on a.id = b.parent_id)
select count(id) as count, generation
from cte
where id not in (select distinct parent_id from ecoli_data where parent_id is not null) -- 왜 parent_id를 not null 해줘야 할까
group by generation
order by generation
-- NULL 값 비교 시 NOT IN이 의도와 다르게 동작 가능
문제풀이
recursive cte :
각 ID가 어떤 세대에 해당하는지 먼저 구해줘야 한다.이를 구하기 위해 재귀함수를 사용해준다.그러면 마지막 세대인 4세대를 구할 때까지 반복되다 멈춘다.그러면 generation, id로 구성된 테이블을 구할 수 있다!
이제 cte를 불러와서 각 세대별 자식이 없는 id를 count해주면 된다.
여기서 주의할 점은 not in을 사용할 때 비교할 서브쿼리에 null값이 있으면 not in 기능이 제대로 동작하지 않는다는 것이다!
느낀 점
이 문제의 포인트는 recursive(재귀함수) 사용과 not in 사용 조건을 아는 것이다.그리고 self join할 때 어떤 테이블의 부모 ID와 자식 ID를 비교해서 가져올 건지 잘 구상해야 한다.

'Tools > - SQL' 카테고리의 다른 글
| [SQL] 📌 중앙값 구하기 | median 함수 없이 구하는 방법 | 활용 예제 (0) | 2025.05.10 |
|---|---|
| [SQL] 프로그래머스 예제 | 보호소에서 중성화한 동물 | regexp 정규표현식 (0) | 2025.03.06 |
| [SQL] solvesql | 배송 예정일 예측 성공과 실패 (0) | 2025.02.14 |
| [SQL] solvesql | 쇼핑몰의 일일 매출액과 ARPPU (0) | 2025.02.14 |
| [SQL] solvesql | 세 명이 서로 친구인 관계 찾기 | self join 활용하기, on절 조건 여러개 (0) | 2025.02.14 |