Как сделать цикл в SQL Server для объединения записей - PullRequest
0 голосов
/ 23 сентября 2019

У меня есть записи, которые объединяются в объединенную запись в SQL Server.И я заинтересован, чтобы перейти к верхней записи с помощью sql.Пример ниже проясняет вопрос.

Tbl_Merge имеет два столбца ChildRecord и ParentRecord:

ChildRecord     ParentRecord
-----------------------------
101             102
102             103
103             104

Я хочу этот вывод:

ChildRecord     ParentRecord
-----------------------------
101             104
102             104
103             104

Ответы [ 3 ]

2 голосов
/ 23 сентября 2019

вы можете использовать рекурсивный CTE.Начинается с записи без дочернего элемента как якорь

; with rcte as
(
    -- anchor member : Parent record
    select  ChildRecord = t.ParentRecord, ParentRecord = NULL, RootRecord = t.ParentRecord
    from    yourtbl t
    where   not exists
            (
                select  *
                from    yourtbl x
                where   x.ChildRecord   = t.ParentRecord
            )

    union all

    -- recursive member
    select  ChildRecord = t.ChildRecord, ParentRecord = t.ParentRecord, RootRecord = r.RootRecord
    from    rcte r
            inner join yourtbl t    on  r.ChildRecord   = t.ParentRecord
)
select  r.ChildRecord, ParentRecord = r.RootRecord
from    rcte r
where   r.ParentRecord  is not null   -- exclude the anchor memmber
0 голосов
/ 23 сентября 2019

Рассмотрим следующую таблицу:

create table t1 ( child char(3), parent char(3))
go
insert into t1 values ( '101', '102')
insert into t1 values ( '102', '103')
insert into t1 values ( '103', '104')
go

В следующем запросе используется самообращенная ссылка Общее выражение таблицы для навигации по отношениям и построения дерева, таблица «x».Для каждого дочернего элемента запрос находит максимальную глубину и возвращает дочерние и родительские значения

with x ( tree, child, parent, depth)
    as
    (
        select
                cast(child as varchar(100)),
                child,
                parent,
                0
            from
                t1
        union all
        select
                cast (x.tree + ':' + t1.child as varchar(100)),
                x.child,
                t1.parent,
                x.depth + 1
            from
                t1,
                x
            where
                x.parent = t1.child
    )
select 
        x1.child,
        x1.parent
    from
        x x1
    where
        x1.depth = 
        (
            select max(x2.depth) from x x2 where x1.child = x2.child
        )
    order by x1.child

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

insert into t1 values ( '120', '110')
insert into t1 values ( '125', '124')
insert into t1 values ( '124', '123')
insert into t1 values ( '123', '110')
go

Результаты:

child parent
----- ------
101   104
102   104
103   104
120   110
123   110
124   110
125   110
0 голосов
/ 23 сентября 2019
create table #temp (ChildRecord int,Parentrecord int)
insert into #temp values(101,102),(102,103),(103,104)


WITH CTE
     AS (SELECT t.ChildRecord,
                t.Parentrecord,
                1 lvl
         FROM #temp t
         UNION ALL
         SELECT c.ChildRecord,
                t.Parentrecord,
                lvl + 1
         FROM #temp t
              INNER JOIN CTE c ON t.ChildRecord = c.Parentrecord),
     CTE2
     AS (SELECT ChildRecord,
                MAX(lvl) maxlvl
         FROM cte
         GROUP BY ChildRecord)
     SELECT c.ChildRecord,
            c.Parentrecord
     FROM cte c
     WHERE EXISTS
     (
         SELECT 1
         FROM cte2 c2
         WHERE c2.maxlvl = c.lvl
               AND c2.ChildRecord = c.ChildRecord
     );
--select * from #temp

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