簡體   English   中英

如何從遞歸CTE中排除條目?

[英]How do I exclude entries from a recursive CTE?

如何使用Sqlite從遞歸CTW中排除條目?

CREATE TABLE GroupMembers (
    group_id        VARCHAR,
    member_id       VARCHAR
);

INSERT INTO GroupMembers(group_id, member_id) VALUES
    ('1', '10'),
    ('1', '20'),
    ('1', '30'),
    ('1', '-50'),
    ('2', '30'),
    ('2', '40'),
    ('3', '1'),
    ('3', '50'),
    ('4', '-10'),
    ('10', '50'),
    ('10', '60');

我想要一個查詢,該查詢將給我(遞歸)組中的成員列表。 但是,第一個字符為“-”的成員表示減號后的id不在組中。

例如,“ 1”的成員是“ 10”,“ 20”,“ 30”和“ -50”。 但是,“ 10”是一個組,因此我們需要添加其子級“ 50”和“ 60”。 但是,“-50”已經是成員,因此我們不能包含“ 50”。 總之,“ 1”的成員是“ 10”,“ 20”,“ 30”,“-50”和“ 60”。

看來此查詢應該工作:

WITH RECURSIVE members(id) AS (
    VALUES('1')
    UNION
    SELECT gm.member_id 
        FROM members m
        INNER JOIN GroupMembers gm ON mg.group_id=m.id
        LEFT OUTER JOIN members e ON '-' || gm.member_id=e.id
        WHERE e.id IS NULL
)
SELECT id FROM members;

但是我得到了錯誤: multiple references to recursive table: members

如何解決/重寫此功能以執行我想要的操作?

注意:結果集中是否返回“ -50”並不重要。

我沒有可用於測試的SQLite,但是假設-50也意味着也應該排除50 ,我想您正在尋找:

WITH RECURSIVE members(id) AS (
    VALUES('1')
    UNION
    SELECT gm.member_id 
    FROM GroupMembers gm 
      JOIN members m ON gm.group_id=m.id
    WHERE member_id not like '-%'
      AND not exists (select 1 
                      from groupMembers g2
                      where g2.member_id = '-'||gm.member_id)
)
SELECT id 
FROM members;

(以上工作在Postgres中)

通常,您從遞歸部分的基表中進行選擇,然后選擇聯接回實際的CTE。 然后,通過常規的where子句對不需要的行進行過濾, where無需再次加入CTE。 遞歸CTE定義為在JOIN沒有找到更多行時終止。

SQLFiddle(Postgres): http ://sqlfiddle.com/#!15/04405/1

需求更改后進行編輯 (已進行了詳細說明):

因為您需要根據行的位置排除行(原始問題中未提供的詳細信息)。 只能在CTE 之外進行過濾。 同樣,我不能僅使用Postgres使用SQLite進行測試:

WITH RECURSIVE members(id, level) AS (
    VALUES('4', 1)
    UNION
    SELECT gm.member_id, m.level + 1
    FROM GroupMembers gm 
      JOIN members m ON gm.group_id=m.id
)
SELECT m.id, m.level
FROM members m
where id not like '-%'
  and not exists (select 1 
                  from members m2
                  where m2.level < m.level 
                    and m2.id = '-'||m.id);

更新的SQLFiddle: http ://sqlfiddle.com/#!15/ec0f9/3

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM