2015-02-12 77 views
0

我有層次數據的表像這樣:拆散分層數據

LEVEL id_value parent_id_value  description 
0 1  505   None    Top Hierarchy 
1 2  1000  505     Sub Hierarchy 
2 2  300   505     Other Sub Hierarchy 
3 3  0040  300     Rookie hierarchy 
4 3  0042  300     Bottom level 

我需要的是一個查詢,會給我這樣的:

0 id_value  3     2     1 
1   40  Rookie hierarchy Other Sub Hierarchy Top Hierarchy 
2   42  Bottom level  Other Sub Hierarchy Top Hierarchy 
3  1000  NULL    Sub Hierarchy  Top Hierarchy 

它看起來應該很簡單但我失去了一些東西...

+0

使用SELECT與PIVOT查詢,它將解決您的問題。 – Rigel1121 2015-02-12 05:51:33

+0

@ Rigel1121,它不足以遞歸地找到父母。 – dmvianna 2015-02-12 05:54:23

+0

層次結構有深度限制? – danihp 2015-02-12 12:59:50

回答

1

我已經翻譯了您的樣本數據要求的SQL查詢。通知比例:

  • 這次旅行是連接表本身一次又一次地
  • 在每個連接上使用表別名是強制性的。
  • 您可以調整此查詢以符合您的一般要求。
  • 要匹配您的數據示例,第二次加入是左加入

這就是:

select 
    coalesce(l3.id_value,l2.id_value) as id_value , 
    l3.description as "3", 
    l2.description as "2", 
    l1.description as "1" 
from t l1 inner join 
    t l2 on l2."LEVEL"=2 and l1.id_value = l2.parent_id_value 
      left outer join 
    t l3 on l3."LEVEL"=3 and l2.id_value = l3.parent_id_value 
where l1.LEVEL = 1 

Check it on sqlFiddle

-1

不知道爲什麼你需要LEVEL列,但簡單的分層查詢應該工作。如果有水平的固定數量只需添加CONNECT_BY_PATH分裂若干列:

-- sample table 
CREATE TABLE TT1 
(ID_VALUE   NUMBER, 
    PARENT_ID_VALUE NUMBER, 
    DESCRIPTION  VARCHAR2(32)); 

-- the query itself 
SELECT ID_VALUE, 
     REGEXP_SUBSTR(SYS_CONNECT_BY_PATH(DESCRIPTION, '/'), '[^/]+', 1, 3) L3, 
     REGEXP_SUBSTR(SYS_CONNECT_BY_PATH(DESCRIPTION, '/'), '[^/]+', 1, 2) L2, 
     REGEXP_SUBSTR(SYS_CONNECT_BY_PATH(DESCRIPTION, '/'), '[^/]+', 1, 1) L1 
    FROM TT1 
    WHERE CONNECT_BY_ISLEAF = 1 
    START WITH PARENT_ID_VALUE IS NULL 
CONNECT BY PARENT_ID_VALUE = PRIOR ID_VALUE 
0

該查詢給所有需要的信息:

select id_value, --parent_id_value piv, description, level tlvl, 
    sys_connect_by_path(description, '/') tpath 
    from hd where connect_by_isleaf = 1 
    start with parent_id_value not in (select id_value from hd) 
    connect by parent_id_value = prior id_value 

結果

id_value tpath 
-------- --------------------------------------------------------------- 
     40 /Top hierarchy/Other sub hierarchy/Rookie hierarchy  
     42 /Top hierarchy/Other sub hierarchy/Bottom level   
    1000 /Top hierarchy/Sub hierarchy 

現在,如果我們假設最大層次結構深度爲3,則此查詢會將子層次結構置於單獨的列中。

with leaves as (
    select id_value, parent_id_value piv, description, level tlvl, 
     sys_connect_by_path(rpad(description, 20), '/') tpath 
    from hd where connect_by_isleaf = 1 
    start with parent_id_value not in (select id_value from hd) 
    connect by parent_id_value = prior id_value) 
select id_value, 
    substr(tpath, 2*20 + 4, 20) l3, 
    substr(tpath, 1*20 + 3, 20) l2, 
    substr(tpath, 0*20 + 2, 20) l1 
    from leaves 

===================================================================== 
id_value L3     L2      L1 
     40 Rookie hierarchy  Other sub hierarchy  Top hierarchy  
     42 Bottom level   Other sub hierarchy  Top hierarchy  
    1000      Sub hierarchy   Top hierarchy  

如果描述長度> 20,則將此值更改爲字段列長度。

這也可以很容易地在PL/SQL中動態完成,例如,通過首先計算深度,通過execute immediate創建具有適當列數的表並將層次結構放入右列。