T-SQL 查询以提取 Parent 的标签和所有 Children 的标签

T-SQL Query to Pull a Parent's Tags and all Children's Tags

背景

我在 SQL 服务器中有一个数据库架构,如下所示:

http://sqlfiddle.com/#!18/dc3cf/3

| id    | tag   | child_id  |
|----   |-----  |---------- |
| 1     | A     |           |
| 1     |       | 4         |
| 2     | C     |           |
| 3     | C     |           |
| 4     | B     |           |
| 4     |       | 5         |
| 5     | D     |           |
| 5     | E     |           |

每个'id'记录可能有一个child(存储在同一个table中)。每个 child 可以有任意数量的子 children。我不知道层次结构级别的数量,但它可能不会超过 10 个级别。

例子中有:

问题

我需要能够查询以获得所有 id 标签的结果,包括它的所有 children 标签。例如,根据上面的 table 数据,我需要输出如下:

| id    | tag   |
|----   |-----  |
| 1     | A     |
| 1     | B     |
| 1     | D     |
| 1     | E     |
| 2     | C     |
| 3     | C     |
| 4     | B     |
| 5     | D     |
| 5     | E     |

请注意,我需要 children 仍然出现。

如果不多次将 table 连接到自身 'n' 中 'n' 是层级数,这是否可能?

编辑

澄清一下,每个id也是一个根元素。因此,了解一个 ID 是否也是 child 的唯一方法是查看该 ID 是否有另一条记录,其中它有一个 child_id。我制作了另一个版本的 SQL Fiddle 来证明这一点。请注意,id 2 现在有一个 child: http://sqlfiddle.com/#!18/422f9/1

| id    | tag   | child_id  |
|----   |-----  |---------- |
| 1     | A     |           |
| 1     |       | 4         |
| 2     | C     |           |
| 2     |       | 5         |
| 3     | C     |           |
| 4     | B     |           |
| 4     |       | 5         |
| 5     | D     |           |
| 5     | E     |           |

是的,不加入tablen次是可以的,可以使用CTE(Common Table Expression),see Docs

在您的情况下,代码应该类似于:

WITH cte (id, tag, child_id, parent) AS
(
    SELECT id, tag, child_id, id
    FROM demo
    WHERE id NOT IN(SELECT child_id FROM demo WHERE child_id IS NOT NULL)
    UNION ALL
    SELECT demo.id, demo.tag, demo.child_id, cte.parent
    FROM demo
        JOIN cte
            ON cte.child_id = demo.id
)
SELECT parent, tag
FROM cte
WHERE tag IS NOT NULL
UNION 
SELECT id, tag
FROM demo
WHERE tag IS NOT NULL
ORDER BY parent, tag

编辑: 动态确定基础元素。