- 概述
递归查询能够完成在 SQL 中无法实现的操作。
本文通过示例对递归查询进行了简单介绍,并展示了与PL/SQL的递归查询实现的差异。 - 公用表表达式(WITH子句)
公用表表达式(CTE)可以被看作是一个视图,只适用于一个单一的查询:
WITH ctename AS (
SELECT …
)
SELECT …
FROM ctename …
这也可以写成 中的子查询FROM,但使用 CTE 有如下优点:
查询变得更具可读性。
您可以在查询中多次引用CTE,并且只会计算一次。
您可以在 CTE 中使用数据修改语句(通常带有RETURNING子句)。
请注意,在KingbaseES V8R3中,总是物化CTE。这意味着,CTE是独立于包含查询计算的。从KingbaseES V8R6开始,CTE 可以“内联”到查询中,这提供了进一步的优化潜力。 - 递归查询的语法
递归查询是使用递归CTE编写的,即包含RECURSIVE关键字的CTE :
WITH RECURSIVE ctename AS (
SELECT /* non-recursive branch, cannot reference “ctename” /
UNION [ALL]
SELECT / recursive branch referencing “ctename” */
)
SELECT …
FROM ctename …
4. 如何处理递归查询
KingbaseES内部使用工作表来处理递归 CTE。这种处理并不是真正的递归,而是迭代:
首先,通过执行 CTE 的非递归分支来初始化工作表。CTE 的结果也用这个结果集初始化。如果递归 CTE 使用UNION而不是UNION ALL,则删除重复的行。
然后,KingbaseES重复以下操作,直到工作表为空:
评估 CTE 的递归分支,用工作表替换对 CTE 的引用。
将所有结果行添加到 CTE 结果。如果UNION用于合并分支,则丢弃重复的行。
用上一步中的所有新行替换工作表(不包括任何已删除的重复行)。
请注意,到目前为止,CTE的自引用分支并未使用完整的 CTE 结果执行,而是仅使用