2015-10-06 129 views
0

这的跟进问题:SQL Server 2008 R2的:递归查询

我有两列分别是可乐COLB表如下所示:

表:测试

create table Test 
(
cola int, 
colb int 
); 
我已经进入

记录是:

Cola Colb 
------------ 
1  2 
1  3 
1  4 
2  5 
2  6 
2  3 
3  2 
3  4 
3  7 
3  10 
10  11 
11  12 
11  13 
11  14 
12  15 
13  16 
14  99 
15  88 
16  77 

注意:现在我想显示谁与我有通过价值连接的唯一记录。例如,如果我将值作为1传递,那么它应该向我显示连接的数字,并形成像树一样的连接。

对于上述要求,我已经得到了如下所示的黑暗骑士的脚本,它可以正常工作。

;WITH CTE AS 
(
    SELECT COLA,COLB,','+CAST(COLA AS VARCHAR(MAX))+',' AS CHCK FROM test WHERE COLA=1 
    UNION ALL 
    SELECT C1.COLA,C1.COLB,C.CHCK+CAST(C1.cola AS VARCHAR(MAX))+',' 
    FROM CTE C INNER JOIN test C1 ON C.colb = C1.cola 
    WHERE CHARINDEX(','+CAST(C.colb AS VARCHAR(MAX))+',',C.CHCK)=0 
), 
OUTERCTE AS 
( 
    SELECT DISTINCT COLA,COLB,ROW_NUMBER() OVER(PARTITION BY Colb ORDER BY Cola) rn FROM CTE --ORDER BY COLA 
) 
SELECT Cola,Colb FROM OUTERCTE 
WHERE rn<=1 
ORDER BY CASE WHEN Cola = 1 THEN 1 ELSE 2 END; 

,给了我这样的:

---------------- 
Cola  Colb 
---------------- 
1   2 
1   3 
1   4 
2   5 
2   6 
3   7 
3   10 
10   11 
11   12 
11   13 
11   14 
12   15 
13   16 
16   77 
15   88 
14   99 

要求:现在我要显示的记录水平。

预期结果

------------------------------ 
    Cola  Colb  Level 
    ------------------------------ 
    1   2   1 
    1   3   1 
    1   4   1 
    2   5   2 
    2   6   2 
    3   7   2 
    3   10   2 
    10   11   3 
    11   12   4 
    11   13   4 
    11   14   4 
    12   15   5 
    13   16   5 
    16   77   6 
    15   88   6 
    14   99   5 

回答

2
;WITH CTE AS 
(
    SELECT COLA,COLB 
       ,','+CAST(COLA AS VARCHAR(MAX))+',' AS CHCK 
       , 1 as lvl FROM #Test WHERE COLA=1 
    UNION ALL 
    SELECT C1.COLA,C1.COLB ,C.CHCK+CAST(C1.cola AS VARCHAR(MAX))+',' 
          , c.lvl+1 
    FROM CTE C INNER JOIN #Test C1 ON C.colb = C1.cola 
    WHERE CHARINDEX(','+CAST(C.colb AS VARCHAR(MAX))+',',C.CHCK)=0 

), 
cte2 as (
select * , ROW_NUMBER() over (partition by colb order by lvl)as rn From CTE 
) 
select cola,colb,lvl from cte2 where rn = 1 
+0

真棒!非常感谢。 – MAK