news 2026/4/18 8:28:46

postgresql递归查询指定搜索顺序的方法

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
postgresql递归查询指定搜索顺序的方法

原文地址

搜索顺序

在使用递归查询进行树遍历计算时,你可能希望按照深度优先或广度优先的顺序对结果进行排序。这可以通过在数据列之外再计算一个排序列来实现,并在最后使用该列对结果进行排序。需要注意的是,这实际上并不会控制查询评估访问行的顺序;这个顺序在 SQL 中始终依赖于具体实现。此方法仅提供了一种在事后对结果进行排序的便捷方式。

创建深度优先顺序

我们可以为每个结果行计算一个数组,用于记录截至目前已访问过的行。例如,考虑以下使用link字段搜索表tree的查询:

WITHRECURSIVE search_tree(id,link,data)AS(SELECTt.id,t.link,t.dataFROMtree tUNIONALLSELECTt.id,t.link,t.dataFROMtree t,search_tree stWHEREt.id=st.link)SELECT*FROMsearch_tree;

要添加深度优先排序信息,可以这样写:

WITHRECURSIVE search_tree(id,link,data,path)AS(SELECTt.id,t.link,t.data,ARRAY[t.id]FROMtree tUNIONALLSELECTt.id,t.link,t.data,path||t.idFROMtree t,search_tree stWHEREt.id=st.link)SELECT*FROMsearch_treeORDERBYpath;

在一般情况下,如果需要使用多个字段来标识一行,可以使用行数组。例如,如果需要追踪字段f1f2

WITHRECURSIVE search_tree(id,link,data,path)AS(SELECTt.id,t.link,t.data,ARRAY[ROW(t.f1,t.f2)]FROMtree tUNIONALLSELECTt.id,t.link,t.data,path||ROW(t.f1,t.f2)FROMtree t,search_tree stWHEREt.id=st.link)SELECT*FROMsearch_treeORDERBYpath;

提示:在常见的只需追踪一个字段的情况下,可以省略ROW()语法。这样可以使用简单数组而非复合类型数组,从而提高效率。

创建广度优先顺序

你可以添加一个列来追踪搜索的深度,例如:

WITHRECURSIVE search_tree(id,link,data,depth)AS(SELECTt.id,t.link,t.data,0FROMtree tUNIONALLSELECTt.id,t.link,t.data,depth+1FROMtree t,search_tree stWHEREt.id=st.link)SELECT*FROMsearch_treeORDERBYdepth;

为了获得稳定的排序,可以将数据列作为次要排序列添加。

提示:递归查询评估算法会以广度优先搜索的顺序产生输出。然而,这是一个实现细节,依赖它可能并不可靠。每一层内的行顺序肯定是未定义的,因此在任何情况下,可能都需要一些显式的排序。

内置语法

PostgreSQL 提供了内置语法来计算深度优先或广度优先的排序列。例如:

WITHRECURSIVE search_tree(id,link,data)AS(SELECTt.id,t.link,t.dataFROMtree tUNIONALLSELECTt.id,t.link,t.dataFROMtree t,search_tree stWHEREt.id=st.link)SEARCH DEPTHFIRSTBYidSETordercolSELECT*FROMsearch_treeORDERBYordercol;
WITHRECURSIVE search_tree(id,link,data)AS(SELECTt.id,t.link,t.dataFROMtree tUNIONALLSELECTt.id,t.link,t.dataFROMtree t,search_tree stWHEREt.id=st.link)SEARCH BREADTHFIRSTBYidSETordercolSELECT*FROMsearch_treeORDERBYordercol;

该语法在内部会被扩展为类似于上述手写形式的内容。SEARCH子句指定了是需要深度优先还是广度优先搜索、用于排序的列列表,以及一个将包含可用于排序的结果数据的列名。该列将隐式添加到 CTE 的输出行中。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/4/16 22:23:08

一个简单想法的实验随笔-胜任能力

假设有100个人,每个人的能力不同,现在仅对于目前这项工作的胜任程度进行度量。 每个人的工作产出以这种方式度量: 工作能力 * 工作意愿 现在有两种方案 一是取前20名重用,然后剥削后80名。前20名工作意愿设置为90%,…

作者头像 李华
网站建设 2026/4/17 13:02:52

中国传统国画期中报告(1)

焦作工贸职业学院毕业设计期中报告学 院 智能工程学院专业计算机应用技术姓名班级学号指导教师 王思源报告时间空着不写已完成任务情况:系统架构设计:已完成国画系统的整体…

作者头像 李华
网站建设 2026/4/8 22:09:46

NewsAPI、Google Search

day39: 外部API封装(NewsAPI、Google Search) 外部API封装(NewsAPI、Google Search) 定义: 1. 概念 把外部 API 封装成你项目里的一个“标准能力模块”,通常要做到: 统一接口(I…

作者头像 李华
网站建设 2026/4/9 16:24:10

2026年私有化部署企业微信SCRM大概要花多少钱?性价比高吗?

一、背景:为什么私有化部署成2026年企业刚需?企业数据安全合规压力正以肉眼可见的速度攀升。最新行业调研显示,超70%企业因成本模糊而在私有化SCRM部署决策上滞后——这背后,是《数据安全法》《个人信息保护法》等政策对企业数据自…

作者头像 李华
网站建设 2026/4/16 13:28:08

20251226_174446_我的RAG开源项目300+star了,十分适合新手入门(日志

三个月前,我在 Github 上开源的一个 RAG 练手项目,目前已经有了 327 个 star,总共解决了 22 个 issues。结合过去几个月的项目实践,我重新对项目做了轻量化重构,降低资源消耗与部署门槛。项目地址:https://…

作者头像 李华
网站建设 2026/4/18 7:53:24

2025年,户外安防的终极形态是否是“零布线+零维护”?“黑夜如白昼”竟是营销话术?户外安防摄像头看着一篇就够了

面对参数复杂的户外摄像头,挑选时往往令人困惑。其实,决定日常90%体验的关键并非参数堆砌,而是回归安防本质:**“看得清、装得易、用得省心”**。抓住以下三个核心维度,即可轻松做出选择。**一、全时清晰画质&#xff…

作者头像 李华