본문 바로가기

데이터베이스/MySQL, MariaDB

MySQL 재귀 쿼리를 활용한 부모 상하 관계 표현하기

부모 자식 관계를 나타내는 재귀쿼리

MySQL에서 재귀 쿼리를 작성하려면 WITH RECURSIVE CTE (Common Table Expressions)를 사용해야 합니다.

가정:

  • 테이블 이름은 myTable입니다.
  • 각 행의 고유 ID는 id 컬럼에 있습니다.
  • 부모 ID는 parent_id 컬럼에 있습니다.

아래는 부모와 자식 관계를 나타내는 재귀 쿼리입니다:

WITH RECURSIVE cte AS (
    SELECT id, parent_id, 1 as depth
    FROM myTable
    WHERE parent_id IS NULL -- 루트 노드를 선택합니다. 필요에 따라 변경할 수 있습니다.

    UNION ALL

    SELECT m.id, m.parent_id, cte.depth + 1
    FROM myTable m
    JOIN cte ON m.parent_id = cte.id
)

SELECT * FROM cte;

이 쿼리는 다음과 같은 방식으로 동작합니다:

  1. 초기 쿼리에서 parent_id가 NULL인 레코드 (즉, 루트 노드)를 선택하고 depth를 1로 설정합니다.
  2. 재귀적 부분에서 이전 단계의 id와 현재 단계의 parent_id를 조인하여 다음 depth의 레코드를 선택합니다. depth는 이전 단계의 값에서 1을 더한 값으로 설정됩니다.
  3. 이 과정이 더 이상 결과를 생성하지 않을 때까지 계속됩니다.

WITH RECURSIVE CTE를 사용하여 부모-자식 관계를 표현하는 재귀 쿼리를 작성할 수 있습니다.


그룹별로 소계 계산하기

그룹별로 소계를 계산하려면 주로 GROUP BY와 SUM을 사용합니다. 여기서는 depth를 기준으로 그룹화하고 각 depth에서의 항목 수를 계산하겠습니다.

먼저, 원래의 쿼리는 myTable에 있는 각 항목의 depth를 계산합니다. 이 depth 값을 기준으로 그룹화하여 각 depth의 항목 수를 계산하겠습니다.

다음은 그룹별로 소계를 계산하는 쿼리입니다:

WITH RECURSIVE cte AS (
    SELECT id, parent_id, 1 as depth
    FROM myTable
    WHERE parent_id IS NULL

    UNION ALL

    SELECT m.id, m.parent_id, cte.depth + 1
    FROM myTable m
    JOIN cte ON m.parent_id = cte.id
)

SELECT depth, COUNT(id) as itemCount
FROM cte
GROUP BY depth
ORDER BY depth;

 

이 쿼리는 각 depth에서의 항목 수를 계산합니다. 필요에 따라 다른 집계 함수와 조건을 추가하여 다양한 방식의 그룹별 소계를 계산할 수 있습니다.

 

 

 

 

 

반응형