【发布时间】:2017-08-01 20:21:56
【问题描述】:
我有一个表,它通过将两个“节点”链接在一起来创建路径。
Node
-----------
Id - Primary Key
Name
etc...
Path
------
Id - Primary Key
From - FK to Node
To - FK to Node
所以这条路:
W --- X --- Y --- Z
可以这样构建:
Node
Id Name
--- -----
1 W
2 X
3 Y
4 Z
5 A
6 B
7 C
Path
Id From To
--- ------- -------
1 1 2
2 2 3
3 3 4
4 6 7
我想出了一个递归 CTE 查询,它给定任何节点 ID,遍历路径并返回所有涉及的“路径”。
declare @nodeId = 2
;WITH cte AS (
-- ANCHOR
-- Find one path involving Node
SELECT top 1 p.*, 0 as [Seq] FROM dbo.Path p WHERE [From] = @nodeId or [To] = @nodeId
union all
-- go left
select leftPath.*, cte.[Seq] - 1 as [Seq]
from [Path] leftPath
join cte on cte.[From] = leftPath.[To] and cte.[Seq] <= 0
union all
-- go right
select rightPath.*, cte.[Seq] + 1 as [Seq]
from [Path] rightPath
join cte on cte.[To] = rightPath.[From] and cte.[Seq] >= 0
)
SELECT cte.Id, cte.Seq, cte.From, cte.To
FROM cte
order by [Seq]
所以这会返回所有路径 -
Path
Id Seq From To
--- --- ------- -------
1 -1 1 2
2 0 2 3
3 1 3 4
但是如何编写一个给定节点 ID 的查询,遍历左右路径并返回所涉及的所有 DISTINCT(有序)节点?
Id Name
--- -----
1 W
2 X
3 Y
4 Z
【问题讨论】:
-
您的查询似乎不起作用,例如
description不存在。请解决这个问题,我会看看rextester.com/DEVHNG47817 -
该查询与您的输出不匹配。不否定
Seq -
有一个问题,您共享一个
LIVE代码,所以当我编辑更改代码时。使用底部的FORK创建一个单独的版本。 -
试试这个? rextester.com/edit/DEVHNG47817 Seq 并不重要,由于 TOP 1 如何获取默认顺序,它可能有所不同,我在其中放置了一个 order by 子句,只是为了与您的示例相匹配。它所做的只是正确排序结果
标签: sql-server recursion common-table-expression