按深度和兄弟订单订购记录

时间:2018-05-12 15:37:49

标签: sqlite sql-order-by common-table-expression singly-linked-list recursive-query

我有一个我想订购的树形结构。垂直和水平。

从SQLite doc我得到了深度排序:

WITH RECURSIVE
  under_alice(name,level) AS (
    VALUES('Alice',0)
    UNION ALL
    SELECT org.name, under_alice.level+1
      FROM org JOIN under_alice ON org.boss=under_alice.name
     ORDER BY 2 DESC
  )
SELECT substr('..........',1,level*3) || name FROM under_alice;

给出了:

Alice
...Bob
......Dave
......Emma
...Cindy
......Fred
......Gail

在该请求中,订单仅在级别上。所以兄弟姐妹(Bob& Cindy,Dave& Emma,Fred& Gail)的顺序不受约束(即它是插入顺序)。

但我还需要订购兄弟姐妹。所以我想到一个带有下一个兄弟的id的兄弟列(如链接列表中)。

该表格为table org (name text, boss name, sibling name)

数据:

'Alice', null, null
'Cindy', 'Alice', 'Bob'
'Bob', 'Alice', null
'Dave', 'Bob', 'Emma'
'Emma', 'Bob', null
'Gail', 'Cindy', 'Fred'
'Fred', 'Cindy', null

结果将是:

Alice
...Cindy
......Gail
......Fred
...Bob
......Dave
......Emma

如何将其集成到递归请求中?

1 个答案:

答案 0 :(得分:1)

要将兄弟规范转换为可用于ORDER BY的格式,请使用另一个递归CTE来计算同一boss下的兄弟节点。因为没有任何东西可以识别第一个兄弟姐妹,所以搜索更容易倒退:

WITH RECURSIVE OrderedOrg(Name, Boss, SiblingOrder) AS (
  SELECT Name, Boss, 0
  FROM org
  WHERE Sibling IS NULL

  UNION ALL

  SELECT org.Name, org.Boss, OrderedOrg.SiblingOrder + 1
  FROM org
  JOIN OrderedOrg ON org.Boss    = OrderedOrg.Boss
                 AND org.Sibling = OrderedOrg.Name
),
under_alice(...) AS (
  ...
  SELECT ...
  FROM ... OrderedOrg ...
  ...
  ORDER BY level DESC, SiblingOrder DESC
)
SELECT ...