Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/67.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
PostrgreSQL中是否有与connectby等价的树?_Sql_Postgresql_Select_Recursive Query - Fatal编程技术网

PostrgreSQL中是否有与connectby等价的树?

PostrgreSQL中是否有与connectby等价的树?,sql,postgresql,select,recursive-query,Sql,Postgresql,Select,Recursive Query,我正在学习如何使用postgresql12中的树,并找到了一个很好的函数connectby 例如: SELECT * FROM connectby('descriptor_value', 'descriptor_value_id', 'parent_value_id', '1', 0, '->') 给出以下输出: 然而,我不想从根开始构建所有的树,我想从节点开始建立到根的分支(性能)。例如,我想作为参数87传递,并获取1->86->87。有这样的功能吗?这通常是通过使用

我正在学习如何使用postgresql12中的树,并找到了一个很好的函数c
onnectby

例如:

SELECT * FROM connectby('descriptor_value', 'descriptor_value_id', 
    'parent_value_id', '1', 0, '->') 
给出以下输出:


然而,我不想从根开始构建所有的树,我想从节点开始建立到根的分支(性能)。例如,我想作为参数
87
传递,并获取
1->86->87
。有这样的功能吗?

这通常是通过使用



由于在Postgres 8.4中引入了递归CTE,因此,
connectby()
函数已经非常过时了


由于Postgres 8.4中引入了递归CTE,因此,
connectby()
函数已经非常过时了

with recursive cte as (
    select descriptor_value_id, parent_value_id, 1 lvl 
    from descriptor_value 
    where descriptor_value_id = 87
    union all
    select dv.descriptor_value_id, dv.parent_value_id, lvl + 1
    from descriptor_value dv
    inner join cte c on c.parent_value_id = dv.descriptor_value_id
)
select string_agg(descriptor_value_id::text, '->' order by lvl desc) full_path from cte
递归查询从给定的
描述符\u值\u id
开始爬树。然后,外部查询通过按与找到位置相反的顺序聚合找到的ID来生成完整路径

这将为您提供一个包含给定节点完整路径的单行和单列结果

您可以通过修改递归查询锚点的
where
子句来更改起始节点


如果要使用相同的逻辑一次获取到每个节点的路径,仍然向上遍历树,可以执行以下操作:

with recursive cte as (
    select descriptor_value_id starting_id, descriptor_value_id, parent_value_id, 1 lvl 
    from descriptor_value 
    union all
    select c.starting_id, dv.descriptor_value_id, dv.parent_value_id, lvl + 1
    from descriptor_value dv
    inner join cte c on c.parent_value_id = dv.descriptor_value_id
)
select 
    starting_id, 
    string_agg(descriptor_value_id::text, '->' order by lvl desc) full_path 
from cte
group by starting_id
但是,在这种情况下,沿着树向下走可能更简单、更有效。

我认为您需要:

with recursive cte as (
    select descriptor_value_id, parent_value_id, 1 lvl 
    from descriptor_value 
    where descriptor_value_id = 87
    union all
    select dv.descriptor_value_id, dv.parent_value_id, lvl + 1
    from descriptor_value dv
    inner join cte c on c.parent_value_id = dv.descriptor_value_id
)
select string_agg(descriptor_value_id::text, '->' order by lvl desc) full_path from cte
递归查询从给定的
描述符\u值\u id
开始爬树。然后,外部查询通过按与找到位置相反的顺序聚合找到的ID来生成完整路径

这将为您提供一个包含给定节点完整路径的单行和单列结果

您可以通过修改递归查询锚点的
where
子句来更改起始节点


如果要使用相同的逻辑一次获取到每个节点的路径,仍然向上遍历树,可以执行以下操作:

with recursive cte as (
    select descriptor_value_id starting_id, descriptor_value_id, parent_value_id, 1 lvl 
    from descriptor_value 
    union all
    select c.starting_id, dv.descriptor_value_id, dv.parent_value_id, lvl + 1
    from descriptor_value dv
    inner join cte c on c.parent_value_id = dv.descriptor_value_id
)
select 
    starting_id, 
    string_agg(descriptor_value_id::text, '->' order by lvl desc) full_path 
from cte
group by starting_id

但是,在这种情况下,向下遍历树可能更简单、更有效。

您可以只交换参数keyid\u fld和parent\u keyid\u fld:

SELECT * FROM connectby('descriptor_value', 'parent_value_id', 'descriptor_value_id', '87', 0, '->')
这应该会让你

87
87->86
87->86->1

您可以交换参数keyid\u fld和parent\u keyid\u fld:

SELECT * FROM connectby('descriptor_value', 'parent_value_id', 'descriptor_value_id', '87', 0, '->')
这应该会让你

87
87->86
87->86->1