我正在对Google Cloud Spanner中的某个东西进行原型设计,并且我需要一种方法来执行递归查询,就像在PostgreSQL / SQLite中那样处理递归查询,以处理数据的层次结构或图形。我正在寻找类似https://sqlite.org/lang_with.html的语法。 Spanner是否有办法执行像这样的递归查询,或者有可能执行类似的递归查询呢?我找不到常见表表达式的语法。
更多详细信息:
好吧,我正在Spanner中建模有向无环图(DAG)。我需要在图表上进行搜索。一个示例查询是:“查找连接到特定节点的所有源”。在Spanner中为图形建模的首次尝试如下:
CREATE TABLE nodes (
node_id INT64 NOT NULL,
node_label String(1024) NOT NULL,
name String(1024)
) PRIMARY KEY (node_id);
CREATE TABLE out_edges (
node_id INT64 NOT NULL,
to_node_id INT64 NOT NULL,
edge_label String(1024) NOT NULL,
) PRIMARY KEY (node_id, to_node_id),
INTERLEAVE IN PARENT nodes ON DELETE CASCADE;
CREATE TABLE in_edges (
node_id INT64 NOT NULL,
from_node_id INT64 NOT NULL,
edge_label String(1024) NOT NULL,
) PRIMARY KEY (node_id, from_node_id),
INTERLEAVE IN PARENT nodes ON DELETE CASCADE;
使用交错表是为了尝试快速访问节点的边缘。 out_edges
和in_edges
表中都存在每个唯一边。
查找图中所有连接到特定节点的源的一种方法是,从该节点开始以相反的顺序沿着边缘进行DFS或BFS,同时跟踪在边缘没有任何节点的节点,如他们被遍历。通过这种表示形式,我可以想到的两种方法是使用递归公用表表达式(例如在SQLite或PostgreSQL中或在Oracle中可以使用CONNECT BY)或维护图形的传递闭包并在无边界的情况下加入节点在传递闭包中与输入节点相邻的那些节点。后者可以在Spanner中使用,但需要所有额外的存储和维护传递关闭。而且,如果没有某种递归查询,我将仅限于查找距输入节点固定数量的边的源。我猜想在Spanner中完成此操作的另一种方法是在客户端代码中执行搜索算法。这样做的问题是,为了满足原始查询,可能会对Spanner进行大量查询。
答案 0 :(得分:2)
Cloud Spanner不支持递归查询。如果您提供有关用例的更多信息,则可能有一个很好的替代解决方案。
https://cloud.google.com/spanner/docs/query-syntax
基于其他上下文:
根据延迟要求和图形的形状/大小,使用客户端代码进行搜索可能很有意义。考虑维护一个单独的交错表来跟踪每个节点的源是否值得。这种方法的推广效果可能不太好,具体取决于您将支持的图形形状和查询。
CREATE TABLE sources (
node_id INT64 NOT NULL,
source_node_id INT64 NOT NULL,
) PRIMARY KEY (node_id, source_node_id),
INTERLEAVE IN PARENT nodes ON DELETE CASCADE;