Parent - дочерний sql запрос
-
05-07-2019 - |
Вопрос
id parent_id
1 0
2 0
3 2
4 0
5 1
6 0
Мне нужен запрос, который будет возвращать родительские строки (parent_id = 0), за которыми следуют его дочерние строки:
<Ол>Ожидаемый результат: упорядочено по id
id parent_id
-------------------------------------------
1 0 (first parent)
5 1 (all children of first parent)
2 0 second parent
3 2 (all children of second parent)
4 0 third parent
6 0 fourth parent
Я могу использовать союз родителей, за которым следуют все дети Но это дает мне сначала родителей, потом детей. Мне нужен родитель и сразу его дети.
Кто-нибудь может помочь?
Решение
Это можно сделать с помощью двух временных таблиц и трех переменных.
CREATE TABLE #Parents ( RowId bigint identity(1,1), Id bigint )
CREATE TABLE #Results ( RowId bigint identity(1,1), Id bigint, ParentId bigint )
DECLARE @Count1 bigint DECLARE @Count2 bigint DECLARE @ParentId bigint
INSERT INTO #Parents SELECT Id FROM MyTable WHERE ParentId = 0 ORDER BY Id
SET @Count1 = 0 SELECT @Count2 = MAX(RowId) FROM #Parents
WHILE @Count1 < @Count2 BEGIN SET @Count1 = @Count1 +1 SELECT @ParentId = Id FROM #Parents WHERE RowId = @Count1 INSERT INTO #Results (Id, ParentId) VALUES (@Count1, 0) INSERT INTO #Results (Id, ParentId) SELECT ID, ParentId FROM MyTable WHERE ID = @Count1 ORDER BY Id END
SELECT Id, ParentId FROM #Results ORDER BY RowId
DROP TABLE #Results DROP TABLE #Parents
Другие советы
Если вы работаете в SQL Server 2005+, вы можете использовать рекурсивный CTE, следя за тем, чтобы в конце вы поддерживали поле, по которому можно было упорядочить.
Попробуйте это:
declare @t table (id int, parent_id int)
insert @t
select 1,0
union all select 2,0
union all select 3,2
union all select 4,0
union all select 5,1
union all select 6,0
;
with tree as (
select t.*, convert(varbinary(max),t.id) as ordered
from @t t
where parent_id = 0
union all
select t.*, ordered + convert(varbinary(max),t.id)
from tree base
join
@t t
on t.parent_id = base.id
)
select *
from tree
order by ordered
;