我有一个像这样的SQL表
ID Name ParentID
------------------------------
1 Alex 0
2 John 0
3 Don 1
4 Philip 2
5 Shiva 2
6 San 3
7 Antony 6
8 Mathew 2
9 Cyril 8
10 Johan 9
-------------------------
我正在寻找像这样的外线
如果我传递ID 7,10
输出表将是
ID Name Relation
------------------------------------
7 Antony Alex->Don->San->Antony
10 Johan John->Mathew->Cyril->Johan
如何使用CTE
实现这一目标答案 0 :(得分:4)
这似乎可以解决问题。关键是要意识到我们可以向后建立路径并在我们不再有父母找到时停止:
DECLARE @t table (ID int not null, Name varchar(19) not null, ParentID int null)
insert into @t(ID,Name,ParentID) values
(1 ,'Alex',null),
(2 ,'John',null),
(3 ,'Don',1),
(4 ,'Philip',2),
(5 ,'Shiva',2),
(6 ,'San',3),
(7 ,'Antony',6),
(8 ,'Mathew',2),
(9 ,'Cyril',8),
(10,'Johan',9)
declare @search table (ID int not null)
insert into @search (ID) values (7),(10)
;With Paths as (
select s.ID as RootID,t.ID,t.ParentID,t.Name, CONVERT(varchar(max),t.Name) as Path
from
@search s
inner join
@t t
on
s.ID = t.ID
union all
select p.RootID,t.ID,t.ParentID,p.Name, t.Name + '->' + p.Path
from Paths p
inner join
@t t
on
p.ParentID = t.ID
)
select * from Paths where ParentID is null
结果:
RootID ID ParentID Name Path
----------- ----------- ----------- ------------------- ----------------------------
10 2 NULL Johan John->Mathew->Cyril->Johan
7 1 NULL Antony Alex->Don->San->Antony
(我已经在其他专栏中留下来帮助显示最终状态。在没有过滤的情况下查询CTE也可能具有指导意义)
我还提醒说,如果可能的话,我通常不会使用分隔字符串 - 当SQL Server的设计类型时,它不是很好的表示使用多个值。
答案 1 :(得分:1)
使用公用表表达式查询:
CREATE TABLE #Table(ID INT,Name VARCHAR(MAX),ParentID INT)
INSERT INTO #Table(ID ,Name ,ParentID)
SELECT 1,'Alex',0 UNION ALL
SELECT 2,'John',0 UNION ALL
SELECT 3,'Don',1 UNION ALL
SELECT 4,'Philip',2 UNION ALL
SELECT 5,'Shiva',2 UNION ALL
SELECT 6,'San',3 UNION ALL
SELECT 7,'Antony',6 UNION ALL
SELECT 8,'Mathew',2 UNION ALL
SELECT 9,'Cyril',8 UNION ALL
SELECT 10,'Johan',9
;WITH Relationship ( _ID , _Name , _Relation , _ParentId) AS
(
SELECT ID , Name , Name , ID
FROM #Table
WHERE ParentID = 0
UNION ALL
SELECT ID , Name , _Relation + '->' + Name , _ParentId
FROM Relationship
JOIN #Table ON _ID = ParentID
)
SELECT _ID ID, _Name Name, _Relation Relation
FROM Relationship
WHERE _ID IN ( SELECT MAX(_ID) FROM Relationship GROUP BY _ParentId)