Simple Graph Search Algorithm in SQL (PostgreSQL)

痴心易碎 提交于 2019-12-02 20:57:42
a_horse_with_no_name

Something like this:

with recursive graph_cte (node1, node2, start_id) 
as
( 
  select node1, node2, id as start_id
  from graphs
  where node1 = 1 -- alternatively elect the starting element using where id = xyz
  union all
  select nxt.node1, nxt.node2, prv.start_id
  from graphs nxt
    join graph_cte prv on nxt.node1 = prv.node2
)
select start_id, node1, node2
from graph_cte
order by start_id;

(requires PostgreSQL 8.4 or higher)

SQL is not best suited to manipulating graphs and finding paths. You're probably better off loading the graph in to a procedural language and using the Floyd-Warshall algorithm or Johnson's algorithm to find a path between nodes.

However, if you really must use SQL then I suggest you pick up a copy of Joe Celko's SQL for Smarties which has an entire chapter devoted to graphs in SQL.

You can use graph database directly to solve your problem: https://launchpad.net/oqgraph -> graph as mysql storage engine

This is not exactly memory-optimal, but works with cyclic graphs too:

with recursive graph_cte (node1, node2, path) 
as
( 
  select node1, node2, ARRAY[node1] as path
  from graph
  where node1 = 4 -- start node
  union all
  select nxt.node1, nxt.node2, array_append(prv.path, nxt.node1)
  from graph nxt, graph_cte prv
  where nxt.node1 = prv.node2
  and nxt.node1 != ALL(prv.path)
)
select array_append(path, node2)
from graph_cte
where node2 = 6 -- goal node
limit 1;

Its based on a previously accepted answer, but keeps track of the path. It should stop searching immediately once it finds the goal node.

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!