【问题标题】:Find a specific parent inside hierarchical data using T-SQL使用 T-SQL 在分层数据中查找特定父级
【发布时间】:2019-04-11 16:47:23
【问题描述】:

我有具有层次顺序的对象。每个对象都有一个 ID、一个父对象(表中的TO_ID)和一个类型。 我的数据在一个看起来像这样的表中:

ID  | TO_ID | TYPE
123 | 103   | group
176 | 103   | field
256 | 169   | group
103 | 234   | organization
234 | 390   | site

现在我想在表格中搜索,直到找到具有特定类型的父对象(我不知道我的起始对象有多少父对象)。

例如我以ID123开头,想用TYPEsite找到父对象的ID

如何用 SQL 解决这个问题?

【问题讨论】:

    标签: sql sql-server tsql hierarchical-data


    【解决方案1】:

    为此,您需要一个递归 CTE:

    DECLARE @t TABLE (ID INT, TO_ID INT, TYPE VARCHAR(100));
    
    INSERT INTO @t VALUES
    (123, 103, 'group'),
    (176, 103, 'field'),
    (256, 169, 'group'),
    (103, 234, 'organization'),
    (234, 390, 'site'),
    (390, 999, 'notme');
    
    DECLARE @start INT = 123;
    DECLARE @stop VARCHAR(100) = 'site';
    
    WITH cte AS (
        SELECT base.*, 1 AS LVL
        FROM @t base
        WHERE ID = @start
        UNION ALL
        SELECT curr.*, LVL + 1
        FROM @t curr
        INNER JOIN cte prev ON curr.ID = prev.TO_ID
        WHERE prev.TYPE <> @stop
    )
    SELECT *
    FROM cte
    ORDER BY LVL
    

    递归 CTE 实际上是一个迭代查询。您从一些行(第 123 行)开始,然后继续将行附加到上一次迭代的结果中,直到满足某些条件(您用完行或在上一次迭代中找到 site)。结果如下:

    ID  | TO_ID | TYPE         | LVL
    123 | 103   | group        | 1
    103 | 234   | organization | 2
    234 | 390   | site         | 3
    

    如果您对查找两个节点之间的完整路径不感兴趣,请从 curr 中删除 where 子句并在最后添加 WHERE TYPE = site

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-10-29
      相关资源
      最近更新 更多