2017-02-02 169 views
4

我在postgres中的表如下所示。將數組中的值解釋爲有向圖中連接的節點的ID。我想是可能的路徑列表(每行的最後一個ID與其他行的第一個ID匹配)PostgreSQL聚合節點遞歸

數據:

foo 
------- 
{1} 
{2,7} 
{3,4} 
{4,6} 
{5} 
{6,8} 
{7} 
{8} 

預期結果:

{1} 
{2,7} 
{3,4,6,8} 
{5} 

我嘗試使用遞歸查詢和窗口函數,但它不工作,因爲我的預期。

+0

所以他們加入只有對最後INT流入排滿足? –

+0

是的,確切地說,我們將每行的最後一個int與其他行中的第一個int進行匹配 – pastDexter

回答

2

你尋找的是這樣的:

WITH RECURSIVE x AS (
     -- choose first level - without more connections 
     SELECT id, id AS full_id, 1 AS level 
      FROM foo 
     WHERE NOT EXISTS (
       SELECT 1 
       FROM foo AS foo2 
       WHERE foo.id != foo2.id 
        AND foo.id[1] = foo2.id[array_length(foo2.id, 1)]) 
     -- add tail 
     UNION ALL 
     SELECT x.id, x.full_id || foo.id[2:array_length(foo.id, 1)], level + 1 
      FROM x 
      JOIN foo ON (
       foo.id != x.id 
       AND foo.id[1] = x.full_id[array_length(x.full_id, 1)] 
       AND array_length(foo.id, 1) != 1) 
), z AS ( 
    -- looks for maximum length 
    SELECT max(level) OVER (PARTITION BY id), * FROM x 
) 
-- choose only with maximum length 
SELECT full_id FROM z WHERE max = level