sql-server-2005 - 如何在 SQL SERVER 2005 中让 parent 给 child 一个 child

标签 sql-server-2005 transitive-closure-table

我有一张这样的 table

childid      parentid
------------------------
1       0
2       1
3       2
4       2
5       3
6       4
7       0
8       7
9       8
10      1

如果我将 childid 设为 5,则 parentid 将为 1(输出)

如果我将 childid 设为 9,则 parentid 将为 7.(输出)

即根 parentid 为 0,查询应该停在那里。

如何解决这样的查询?

请帮忙。

最佳答案

我认为您应该将 child_id 重命名为 node,将 parent_id 重命名为 child_of。您的列命名有点困惑

create table stack_overflow
(
node int, child_of int
);


insert into stack_overflow(node, child_of) values
(1,0),
(2,1),
(3,2),
(4,2),
(5,3),
(6,4),
(7,0),
(8,7),
(9,8),
(10,1);

这适用于任何支持 CTE 的 RDBMS:

with find_parent(parent, child_of, recentness) as
(
    select node, child_of, 0 
    from stack_overflow
    where node = 9
    union all
    select i.node, i.child_of, fp.recentness + 1
    from stack_overflow i
    join find_parent fp on i.node = fp.child_of
)
select top 1 parent from find_parent 
order by recentness desc

输出:

parent
7

[编辑:更灵活且面向 future ]:

with find_parent(node_group, parent, child_of, recentness) as
(
    select node, node, child_of, 0
    from stack_overflow
    where node in (5,9)
    union all
    select fp.node_group, i.node, i.child_of, fp.recentness + 1
    from stack_overflow i
    join find_parent fp on i.node = fp.child_of
)
select q.node_group as to_find, parent as found 
from find_parent q 
join
(
    select node_group, max(recentness) as answer
    from find_parent
    group by node_group 
) as ans on q.node_group = ans.node_group and q.recentness = ans.answer 
order by to_find    

输出:

to_find     found
5           1
9           7

如果您使用 Postgres,上述代码可以缩短为:

with recursive find_parent(node_group, parent, child_of, recentness) as
(
    select node, node, child_of, 0
    from stack_overflow
    where node in (5,9)
    union all
    select fp.node_group, i.node, i.child_of, fp.recentness + 1
    from stack_overflow i
    join find_parent fp on i.node = fp.child_of
)
select distinct on (node_group) node_group as to_find, parent as found 
from find_parent 
order by to_find, recentness desc

在岩石上与众不同! :-)

关于sql-server-2005 - 如何在 SQL SERVER 2005 中让 parent 给 child 一个 child ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1104977/

相关文章:

SQL Server 2005 - 达到表行大小限制

sql - IIF(...) 不是公认的内置函数

sql - 根据选择的另一行更新行,无需声明变量

mysql - 使用 MySQL 移动传递闭包子树

sql-server - 分层 SQL 数据(递归 CTE、HierarchyID、闭包表)

sql - Service Broker 消息处理顺序

mysql - 对闭包表分层数据结构中的子树进行排序

mysql - SQL 中带闭包表的有向循环图

sql-server-2005 - 查询中的疑问 - SQL Server 2005