Sql server 查找多父层次结构数据模型[SQL Server]中两个节点之间的所有可能关系

Sql server 查找多父层次结构数据模型[SQL Server]中两个节点之间的所有可能关系,sql-server,database,Sql Server,Database,我有一个数据模型来定义多父层次数据。每个记录将表示两个节点的关系,其中一个是父节点,另一个是子节点。在我的例子中,一个节点可以有多个父节点。我需要找到两个节点之间所有可能的关系 以下表为例。 这将形成如下图所示的图形 在上面的模型中,A和B将是顶级节点,每个节点都有两个子节点。节点D被指定为节点A和B的子节点。节点I也被指定为节点D和节点E的子节点。所有其他节点只有一个父节点 我需要编写一个查询来显示一个节点与另一个节点的所有可能关系。 比如说, A和C有关系,因为C是节点A的子节点 A和D有关

我有一个数据模型来定义多父层次数据。每个记录将表示两个节点的关系,其中一个是父节点,另一个是子节点。在我的例子中,一个节点可以有多个父节点。我需要找到两个节点之间所有可能的关系

以下表为例。 这将形成如下图所示的图形 在上面的模型中,A和B将是顶级节点,每个节点都有两个子节点。节点D被指定为节点A和B的子节点。节点I也被指定为节点D和节点E的子节点。所有其他节点只有一个父节点

我需要编写一个查询来显示一个节点与另一个节点的所有可能关系。 比如说,

  • A和C有关系,因为C是节点A的子节点
  • A和D有关系,因为D是节点A的子节点
  • A和G有关系,因为G是节点A的孙子
  • 这将适用于任何级别
  • 如果任何一个节点不是另一个节点的子节点或第n级孙子节点,则两个节点没有任何关系
  • 如果两个节点没有任何关系,它将不会显示。

    上图的最终结果如下:,
    我是SQL Server新手。请帮我解决这个查询。

    通过做一些研究,我能够自己编写查询。正如@SeanLange在注释中指出的,这种类型的查询称为递归CTE

    如果表名为
    节点
    ,下面的查询将创建新表
    关系
    ,并在其中存储我问题中提到的所有可能的关系

    ;with cte as (
        select  child_node
        ,       parent_node
        ,       child_node as root
        from    nodes
        union all
        select  child.child_node
        ,       child.parent_node
        ,       parent.root
        from    cte parent
        join    nodes child
        on      parent.parent_node = child.child_node
    )
    select parent_node,
           root as child_node
    into   relationship
    from   cte
    where  parent_node is not null;
    
    select * from relationship;
    

    它被称为递归cte。在这个网站和互联网的其他地方,有成千上万的关于如何做到这一点的例子。@SeanLange,谢谢你的提示。我已经开始研究递归cte。做得好。有时它只是知道要寻找什么。很高兴你自己解决了D
            A   B
           / \ / \    
          C   D   E
        /  \   \ / \
       G    H   I   J
    
    ----------------------------
    | parent_node | child_node |
    ----------------------------
    | A           | C          |
    | A           | D          |
    | C           | G          |
    | C           | H          |
    | D           | I          |
    | A           | G          |
    | A           | H          |
    | A           | I          |
    | B           | D          |
    | B           | E          |
    | B           | I          |
    | E           | I          |
    | E           | J          |
    | B           | J          |
    ----------------------------
    
    ;with cte as (
        select  child_node
        ,       parent_node
        ,       child_node as root
        from    nodes
        union all
        select  child.child_node
        ,       child.parent_node
        ,       parent.root
        from    cte parent
        join    nodes child
        on      parent.parent_node = child.child_node
    )
    select parent_node,
           root as child_node
    into   relationship
    from   cte
    where  parent_node is not null;
    
    select * from relationship;