列出枢轴 table 中每个级别存在的特定节点的所有祖先或父节点,其中包含级别作为 SQL 服务器中的属性
List all the ancestors or parent nodes of a particular node present at each level in pivoted table containing levels as attributes in SQL Server
我有一个 table 'temp',它有 id 和它的直接父级的 id 作为列。 table如下:
1
/ \
2 3
/|\ \
4 5 6 7
/
8
节点的层次结构可以用上面的树结构表示。
现在,我想使用具有级别的 递归 cte 列出枢轴 table 中所有级别中存在的每个节点的所有祖先节点或父节点(如 Level1 , Level2 等)作为其属性。为了获得此输出,我计算了非透视 table 中的所有父节点以及每个节点相对于其父节点的级别。 sql 查询如下:
WITH ctetable as
(
SELECT S.id, S.parent, 1 as level
FROM temp as S where S.parent is not null
UNION ALL
SELECT S2.id, p.parent, p.level + 1
FROM ctetable AS p JOIN temp as S2 on S2.parent = p.id
)
SELECT * FROM ctetable ORDER BY id;
上述查询的输出如下所示:
但是,我想在特定节点的每个级别下旋转包含父 ID 的递归 cte。比如说,对于id=4,它应该分别在Level3、Level2和Level1下显示parent id 4、2和1。为此,我编写了以下查询:
WITH ctetable as
(
SELECT S.id, S.parent, 1 as level
FROM temp as S where S.parent is not null
UNION ALL
SELECT S2.id, p.parent, p.level + 1
FROM ctetable AS p JOIN temp as S2 on S2.parent = p.id
)
SELECT
myid,
[pn].[1] AS [Level1],
[pn].[2] AS [Level2],
[pn].[3] AS [Level3]
FROM
(
SELECT [a].id,
[a].id as myid,
[a].level
FROM ctetable AS [a]
) AS [hn] PIVOT(max([hn].id) FOR [hn].level IN([1],[2],[3])) AS [pn]
但是,输出 table 不是所需的,因为它包含与特定节点的每个级别下的父 ID 重复的相同 ID,而不是它应该包含该节点在不同级别下的所有父节点。执行上述查询后得到的输出如下所示:
谁能帮我解决这个问题....
如果您有已知的或最大级别数,并且假设我没有反转您想要的结果。
另外 如果您 post 将数据和所需结果作为文本而不是图像作为样本最好
例子
Declare @YourTable Table ([id] int,[parent] int)
Insert Into @YourTable Values
(1,null)
,(2,1)
,(3,1)
,(7,3)
,(4,2)
,(5,2)
,(6,2)
,(8,4)
;with cteP as (
Select id
,Parent
,PathID = cast(10000+id as varchar(500))
From @YourTable
Where Parent is Null
Union All
Select id = r.id
,Parent = r.Parent
,PathID = cast(concat(p.PathID,',',10000+r.id) as varchar(500))
From @YourTable r
Join cteP p on r.Parent = p.id)
Select ID
,B.*
From cteP A
Cross Apply (
Select Level1 = xDim.value('/x[1]','int')-10000
,Level2 = xDim.value('/x[2]','int')-10000
,Level3 = xDim.value('/x[3]','int')-10000
,Level4 = xDim.value('/x[4]','int')-10000
,Level5 = xDim.value('/x[5]','int')-10000
From (Select Cast('<x>' + replace(PathID,',','</x><x>')+'</x>' as xml) as xDim) as X
) B
Order By PathID
Returns
编辑 - 添加了 +10000
我添加了 +10000 以便保持顺序
我有一个 table 'temp',它有 id 和它的直接父级的 id 作为列。 table如下:
1
/ \
2 3
/|\ \
4 5 6 7
/
8
节点的层次结构可以用上面的树结构表示。
现在,我想使用具有级别的 递归 cte 列出枢轴 table 中所有级别中存在的每个节点的所有祖先节点或父节点(如 Level1 , Level2 等)作为其属性。为了获得此输出,我计算了非透视 table 中的所有父节点以及每个节点相对于其父节点的级别。 sql 查询如下:
WITH ctetable as
(
SELECT S.id, S.parent, 1 as level
FROM temp as S where S.parent is not null
UNION ALL
SELECT S2.id, p.parent, p.level + 1
FROM ctetable AS p JOIN temp as S2 on S2.parent = p.id
)
SELECT * FROM ctetable ORDER BY id;
上述查询的输出如下所示:
但是,我想在特定节点的每个级别下旋转包含父 ID 的递归 cte。比如说,对于id=4,它应该分别在Level3、Level2和Level1下显示parent id 4、2和1。为此,我编写了以下查询:
WITH ctetable as
(
SELECT S.id, S.parent, 1 as level
FROM temp as S where S.parent is not null
UNION ALL
SELECT S2.id, p.parent, p.level + 1
FROM ctetable AS p JOIN temp as S2 on S2.parent = p.id
)
SELECT
myid,
[pn].[1] AS [Level1],
[pn].[2] AS [Level2],
[pn].[3] AS [Level3]
FROM
(
SELECT [a].id,
[a].id as myid,
[a].level
FROM ctetable AS [a]
) AS [hn] PIVOT(max([hn].id) FOR [hn].level IN([1],[2],[3])) AS [pn]
但是,输出 table 不是所需的,因为它包含与特定节点的每个级别下的父 ID 重复的相同 ID,而不是它应该包含该节点在不同级别下的所有父节点。执行上述查询后得到的输出如下所示:
谁能帮我解决这个问题....
如果您有已知的或最大级别数,并且假设我没有反转您想要的结果。
另外 如果您 post 将数据和所需结果作为文本而不是图像作为样本最好
例子
Declare @YourTable Table ([id] int,[parent] int)
Insert Into @YourTable Values
(1,null)
,(2,1)
,(3,1)
,(7,3)
,(4,2)
,(5,2)
,(6,2)
,(8,4)
;with cteP as (
Select id
,Parent
,PathID = cast(10000+id as varchar(500))
From @YourTable
Where Parent is Null
Union All
Select id = r.id
,Parent = r.Parent
,PathID = cast(concat(p.PathID,',',10000+r.id) as varchar(500))
From @YourTable r
Join cteP p on r.Parent = p.id)
Select ID
,B.*
From cteP A
Cross Apply (
Select Level1 = xDim.value('/x[1]','int')-10000
,Level2 = xDim.value('/x[2]','int')-10000
,Level3 = xDim.value('/x[3]','int')-10000
,Level4 = xDim.value('/x[4]','int')-10000
,Level5 = xDim.value('/x[5]','int')-10000
From (Select Cast('<x>' + replace(PathID,',','</x><x>')+'</x>' as xml) as xDim) as X
) B
Order By PathID
Returns
编辑 - 添加了 +10000
我添加了 +10000 以便保持顺序