使用WITH循环SQL中的一组数据

Scr*_*Guy 1 sql t-sql sql-server loops

鉴于以下字段,我试图循环到整个迭代集的第一次迭代.

+-------------------+----------------------+------------------------+
|           id      |     nextiterationId  |      iterationCount    | 
+-------------------+----------------------+------------------------+
|           110001  |             110002   |      0                 |
|           110002  |             110003   |      1                 |
|           110003  |             110004   |      2                 |
|           110004  |             1        |      3                 |
Run Code Online (Sandbox Code Playgroud)

因此,如果我使用id字段的一个值调用SP /函数,我需要它返回给定的id的先前迭代,直到iterationCount = 0.

所以,如果我使用id 110003(发送它作为参数),它应该首先查询的是一个id具有a nextIterationID的字段110003.这将是第一个循环.

由于iterationCount还不是0,它会保持循环.然后,它会寻找一个id其中nextIterationID110002基于第一循环的决心,所以第二个循环会发现"身份证"的110001,并将其返回.并且由于记录iterationCount = 0,它将停止循环.

如果我使用SP /函数调用它是没关系的110003,这是第3次迭代,并且它不会返回第1100044次迭代.鉴于id,我只需要它回去.

前一段时间我使用WITH和也许WHILE以某种方式使用它们,但我现在不记得如何做到这一点.我需要以某种方式返回的格式,以便我可以在更大的SELECT语句中使用它.

Ste*_*han 6

这是一个递归的cte解决方案.如果需要任何调整,请告诉我.

--Throwing your table into a temp table
CREATE TABLE #yourTable (ID INT,NextIterationID INT,IterationCount INT)
INSERT INTO #yourTable
VALUES
    (110001,110002,0),
    (110002,110003,1),
    (110003,110004,2),
    (110004,1,3)

--Now for the actual work
--Here is your parameter
DECLARE @param INT = 110003;

--Recursive CTE
WITH yourCTE
AS
(
    --Initial Row
    SELECT  ID,
            NextIterationID,
            IterationCount
    FROM    #yourTable
    WHERE   NextIterationID = @param

    UNION ALL

    --Finding all previous iterations
    SELECT  #yourTable.*
    FROM    #yourTable
    INNER JOIN yourCTE
    ON yourcte.ID = #yourTable.NextIterationID
    --Where clause is not really necessary because once there are no more previous iterations, it will automatically stop
    --WHERE yourCTE.IterationCount >= 0
)

SELECT *
FROM yourCTE

--Cleanup
DROP TABLE #yourTable
Run Code Online (Sandbox Code Playgroud)

结果:

ID          NextIterationID IterationCount
----------- --------------- --------------
110002      110003          1
110001      110002          0
Run Code Online (Sandbox Code Playgroud)