Sql server 如何从sql中的自引用表中获取子数据

Sql server 如何从sql中的自引用表中获取子数据,sql-server,ssrs-2012,Sql Server,Ssrs 2012,我使用的是sql 2012,我有一个具有3个级别的自引用表。表格结构如下: 表结构 我有另一个表引用这个表,它的ID是外键,所以如果这个表的外键是6,我需要显示6是“AAA”,它是“AA”的子节点,是“a”的子节点。我需要向下钻到较低的层次,从较低的层次我应该能够上升到较高的层次。现在我可以升到第二级了 下面是引用另一个表的表的结构。 因此,我想报告这两个表,最终输出应如下所示: 如果我的问题不太清楚,请提问,我会尝试澄清。假设类别树的深度不超过3级,这应该可以: declare @Cat

我使用的是sql 2012,我有一个具有3个级别的自引用表。表格结构如下:

表结构

我有另一个表引用这个表,它的ID是外键,所以如果这个表的外键是6,我需要显示6是“AAA”,它是“AA”的子节点,是“a”的子节点。我需要向下钻到较低的层次,从较低的层次我应该能够上升到较高的层次。现在我可以升到第二级了

下面是引用另一个表的表的结构。

因此,我想报告这两个表,最终输出应如下所示:


如果我的问题不太清楚,请提问,我会尝试澄清。

假设类别树的深度不超过3级,这应该可以:

declare @Catergory table (
    ID int not null,
    Name nvarchar(10) not null,
    ParentID int null
)
declare @Customer table (
    ID int not null,
    Name nvarchar(10) not null,
    SurName nvarchar(10) not null,
    Address nvarchar(30) not null,
    CategoryId int not null
)
insert into @Catergory (ID, Name, ParentID)
values (1, 'A', null), (2, 'B', null),
    (3, 'C', null), (4, 'AA', 1),
    (5, 'CC', 3), (6, 'AAA', 4),
    (7, 'BB', 2), (8, 'AAA', 4),
    (9, 'CCC', 5), (10, 'AA', 1)

insert into @Customer (ID, Name, SurName, Address, CategoryId)
values (1, 'Duck', 'Duffy', '10 Steet', 10),
 (2, 'Ben', 'Ten', '10 Steet', 6),
 (3, 'Cat', 'Dog', '10 Steet', 5),
 (4, 'Chicken', 'Wings', '10 Steet', 1),
 (5, 'Fish', 'Water', '10 Steet', 7)

-- build structure using assumption that the depth is max three levels

select *
from @Customer cust
    join (
        select ID, Name as CategoryName, null As CategoryType, null as SubCategory from @Catergory roots where ParentID is null
        union
        select mids.ID, roots.Name, mids.Name, null from @Catergory mids
            join @Catergory roots on mids.ParentID = roots.ID and roots.ParentID is null
        union
        select leafs.ID, roots.Name, mids.Name, leafs.Name from @Catergory leafs
            join @Catergory mids on leafs.ParentID = mids.ID 
            join @Catergory roots on mids.ParentID = roots.ID and roots.ParentID is null
    ) as struct on cust.CategoryId = struct.ID
order by cust.id
输出:

+----+---------+---------+----------+------------+----+--------------+--------------+-------------+
| ID |  Name   | SurName | Address  | CategoryId | ID | CategoryName | CategoryType | SubCategory |
+----+---------+---------+----------+------------+----+--------------+--------------+-------------+
|  1 | Duck    | Duffy   | 10 Steet |         10 | 10 | A            | AA           | NULL        |
|  2 | Ben     | Ten     | 10 Steet |          6 |  6 | A            | AA           | AAA         |
|  3 | Cat     | Dog     | 10 Steet |          5 |  5 | C            | CC           | NULL        |
|  4 | Chicken | Wings   | 10 Steet |          1 |  1 | A            | NULL         | NULL        |
|  5 | Fish    | Water   | 10 Steet |          7 |  7 | B            | BB           | NULL        |
+----+---------+---------+----------+------------+----+--------------+--------------+-------------+

还有一些额外的栏目在那里,但我相信你可以摆脱它们。但是请注意,某些cartegory列具有
null
值。这是因为,如果客户属于顶级或中级类别,则没有合理的方法填写这些列。

发布您当前的尝试和预期的输出。为什么不使用
hierarchyid
?级别的数量是固定的吗?如果是,您不需要递归或CTE,只需要3个自连接。代码将比CTENO更简单,性能也要快得多。
CategoryName
CategoryType
子类别
。什么是
类型
?这是CategoryName子级,如果类别名称为A,则CategoryType为AA,子类别将为AAA,很抱歉命名不正确。非常感谢,我已尝试将其存档好几天了。你是个明星。它工作得很好。