Как рекурсивно расширить родительско-дочернюю иерархию с помощью CTE - PullRequest
1 голос
/ 16 октября 2019

Я пытаюсь развернуть таблицу со ссылками на себя, используя CTE в базе данных SQL Azure, но пока не заставил ее работать.

В исходной таблице есть столбцы Id, ParentId, например:

Id    ParentId
1     NULL
2     1
3     2
4     2
5     4
6     4
7     NULL
8     7

Я хочу получить следующий результат: (строка для каждого идентификатора и его ребенка или внука или ...)

Id    ChildId
1     1
1     2
1     3
1     4
1     5
1     6
2     2
2     3
2     4
2     5
2     6
3     3
4     4
4     5
4     6
5     5
6     6
7     7
7     8
8     8

Любой способ сделать это с помощью CTE или, возможно,Табличная функция SQL?

Ответы [ 2 ]

0 голосов
/ 16 октября 2019

Для этого вам нужен рекурсивный CTE:

with cte as (
      select id, id as childid, 1 as lev
      from t
      -- where parentid is null
      union all
      select cte.id, t.id, lev + 1
      from cte join
           t
           on cte.childid = t.parentid
      where lev < 10 and t.id <> cte.id
     )
select id, childid
from cte
order by id, childid;

Здесь - это скрипта db <>.

0 голосов
/ 16 октября 2019

https://docs.microsoft.com/en-us/sql/t-sql/queries/with-common-table-expression-transact-sql?view=sql-server-ver15

Я бы использовал пример кода в приведенной выше ссылке в качестве отправной точки. Этот фрагмент кода опирается на популярную базу данных AdventureWorks.

F. Использование рекурсивного общего табличного выражения для отображения иерархического списка

USE AdventureWorks2012;  
GO  
WITH DirectReports(Name, Title, EmployeeID, EmployeeLevel, Sort)  
AS (SELECT CONVERT(varchar(255), e.FirstName + ' ' + e.LastName),  
        e.Title,  
        e.EmployeeID,  
        1,  
        CONVERT(varchar(255), e.FirstName + ' ' + e.LastName)  
    FROM dbo.MyEmployees AS e  
    WHERE e.ManagerID IS NULL  
    UNION ALL  
    SELECT CONVERT(varchar(255), REPLICATE ('|    ' , EmployeeLevel) +  
        e.FirstName + ' ' + e.LastName),  
        e.Title,  
        e.EmployeeID,  
        EmployeeLevel + 1,  
        CONVERT (varchar(255), RTRIM(Sort) + '|    ' + FirstName + ' ' +   
                 LastName)  
    FROM dbo.MyEmployees AS e  
    JOIN DirectReports AS d ON e.ManagerID = d.EmployeeID  
    )  
SELECT EmployeeID, Name, Title, EmployeeLevel  
FROM DirectReports   
ORDER BY Sort;

Схема AdventureWorks

Здесь можно получить диаграмму Visio ER https://www.microsoft.com/en-us/download/confirmation.aspx?id=10331

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...