我如何故意获得相当于“交叉产品”(在SQL Server中)?

时间:2014-12-08 03:34:00

标签: sql sql-server cross-product

我在我的数据库中管理了父子关系,如下所示:

ID   |   ParentID    
A    |    <NULL>    
B    |    A    
C    |    A    
E    |    <NULL>    
F    |    E    

我想构建一个表值函数,它将返回一个表,该表基本上允许您轻松确定属于“家族”的所有其他项目(跟踪父项是非常重要的,但它如果这可能是结果的一部分会很好的)看起来像这样:

ID   | Group Member    
A    |    A    
A    |    B    
A    |    C    
B    |    A    
B    |    B    
B    |    C  
C    |    A    
C    |    B    
C    |    C  
E    |    E    
E    |    F    
F    |    E    
F    |    F

你可以看到,我基本上想要将属于“家庭”一部分的每一条记录与属于一个家庭的其他所有成员相匹配。这只是让我感到尖叫,有一个相当简单的方法可以做到这一点,但我刚刚用这个打击我的头撞墙

2 个答案:

答案 0 :(得分:1)

对于具有自身的表,加入ISNULL(父,ID)应返回所需的结果。

declare @a Table (ID varchar(10),Parent Varchar(10))
Insert into @a Values ('A',NULL) ,('B' , 'A'),('C','A'),('E',NULL) ,('F','E')
Select a.ID,b.ID  as GroupMember
from @a a
JOIN @a b ON ISNULL(a.Parent,a.ID)=ISNULL(b.Parent,b.ID) 

答案 1 :(得分:0)

这不是一个交叉产品;它是一个递归/分层查询。假设关系中没有循环,您可以这样做:

with cte as (
      select id, id as groupmember
      from table t
      where parent is not null
      union all
      select cte.id, t.id as groupmember
      from table t join
           cte
           on cte.parentid = t.id
    )
select *
from cte;