2014-10-10 158 views

回答

0

您需要有父子層次結構才能執行該操作。我用了HR默認模式來執行這個查詢:

with t(val, lvl) as (
select sys_connect_by_path(employee_id, '/'), level lvl 
    from employees 
start with manager_id is null 
connect by manager_id = prior employee_id 
), t_corr(bigboss, boss, employee) as (
select case 
     when lvl > 1 then 
      substr(val, instr(val, '/', 1, 1) + 1, instr(val, '/', 1, 2) - 1 - instr(val, '/', 1, 1)) 
     else 
      substr(val, instr(val, '/', 1, 1) + 1) 
     end bigboss 
    , case 
     when lvl = 1 then null 
     when lvl = 2 then 
      substr(val, instr(val, '/', 1, 2) + 1) 
     else 
     substr(val, instr(val, '/', 1, 2) + 1, instr(val, '/', 1, 3) - 1 - instr(val, '/', 1, 2)) 
     end boss 
    , case 
    when lvl in (1, 2) then null 
     else substr(val, instr(val, '/', 1, 3) + 1) 
     end employee 
    from t 
where lvl < 4 
) 
select e1.last_name || ' ' || e1.first_name bigboss 
    , e2.last_name || ' ' || e2.first_name boss 
    , e3.last_name || ' ' || e3.first_name employee 
    from t_corr 
    , employees e1 
    , employees e2 
    , employees e3 
where t_corr.bigboss = e1.employee_id(+) 
    and t_corr.boss = e2.employee_id(+) 
    and t_corr.employee = e3.employee_id(+) 
/

BIGBOSS    BOSS     EMPLOYEE 
-------------------- -------------------- -------------------- 
King Steven 
King Steven   Kochhar Neena 
King Steven   Kochhar Neena  Greenberg Nancy 
King Steven   Kochhar Neena  Whalen Jennifer 
King Steven   Kochhar Neena  Higgins Shelley 
King Steven   De Haan Lex 
King Steven   De Haan Lex   Hunold Alexander 
King Steven   Raphaely Den 
... 
King Steven   Fripp Adam   Atkinson Mozhe 
King Steven   Fripp Adam   Marlow James 
King Steven   Fripp Adam   Olson TJ 

29 rows selected. 

如果你想從表中做出層次:

with t(a, b, c, d, e) as (
    select 'a', 'b', 'c', 'd', 'e1' from dual union all 
    select 'a', 'b', 'c', 'd', 'e2' from dual union all 
    select 'a', 'b', 'c', 'd', 'e3' from dual union all 
    select 'a', 'b', 'c', 'd', 'e4' from dual union all 
    select 'a', 'b', 'c', 'd', 'e5' from dual union all 
    select 'a', 'b', 'c', 'd', 'e6' from dual union all 
    select 'a', 'b', 'c', 'd', 'e7' from dual union all 
    select 'a', 'b', 'c', 'd', 'e8' from dual 
), tt (a, b, c, d, e) as (
    select a, lpad(b, 4, '-'), lpad(c, 8, '-'), lpad(d, 12, '-'), lpad(e, 16, '-') from t 
) 
select unique dd 
    from tt 
unpivot(
    dd for col1 in (a, b, c, d, e) 
) 
order by 1 

DD 
-------------------- 
a 
---b 
-------c 
-----------d 
--------------e1 
--------------e2 
--------------e3 
--------------e4 
--------------e5 
--------------e6 
--------------e7 
--------------e8 
+0

我知道如何創建一個層次,但在我的表第一列包含頂級節點,第二個包含兩個級別的節點等等...我有五列,並想創建一個5級的樹。請參閱此鏈接 - (http://imgur.com/OrvKgCU) – 2014-10-10 09:30:18

+0

查看我更新的帖子 – zaratustra 2014-10-10 09:57:02

0

我建議你改變你的表結構是這樣的:

emp_id   emp_name   emp_emp_id (boss of emp_id) 
1     BigBoss   NULL 
2     Boss    1 
3     Emp1    2 
4     Emp2    2 

的,你可以easyly使用Oracle關鍵字連接到恢復層次樹。 Doc Here =>http://docs.oracle.com/cd/B19306_01/server.102/b14200/queries003.htm

+0

我知道如何創建一個層次結構,但在我的表中,第一列包含頂層節點,第二層包含第二層的節點,等等......我有五列,並且想要創建一個5層的樹。請參考此鏈接 - (http://imgur.com/OrvKgCU) – 2014-10-10 09:28:35

0

我們以SCOTT.EMP表爲例來創建層次結構。

SQL> SELECT empno, 
    2 level, 
    3 Lpad(ename,LENGTH(ename) + LEVEL * 10 - 10,'-') tree, 
    4 job, 
    5 mgr 
    6 FROM emp 
    7 START WITH mgr  IS NULL 
    8 CONNECT BY PRIOR empno = mgr 
    9/

    EMPNO  LEVEL TREE        JOB    MGR 
---------- ---------- ----------------------------------- --------- ---------- 
     7839   1 KING        PRESIDENT 
     7566   2 ----------JONES      MANAGER   7839 
     7788   3 --------------------SCOTT   ANALYST   7566 
     7876   4 ------------------------------ADAMS CLERK   7788 
     7902   3 --------------------FORD   ANALYST   7566 
     7369   4 ------------------------------SMITH CLERK   7902 
     7698   2 ----------BLAKE      MANAGER   7839 
     7499   3 --------------------ALLEN   SALESMAN  7698 
     7521   3 --------------------WARD   SALESMAN  7698 
     7654   3 --------------------MARTIN   SALESMAN  7698 
     7844   3 --------------------TURNER   SALESMAN  7698 
     7900   3 --------------------JAMES   CLERK   7698 
     7782   2 ----------CLARK      MANAGER   7839 
     7934   3 --------------------MILLER   CLERK   7782 

14 rows selected. 

SQL> 

您需要了解三個重要的事情,START WITHCONNECT BY PRIORLEVEL

START - 指定層次的根。確定從哪裏開始解析。

CONNECT BY PRIOR - 這解釋了父母與孩子之間的關係。以前連接empno = mgr表示我們正在穿越top to bottom。反轉意味着bottom to top

LEVEL - 它像一個僞列一樣顯示層次結構中特定行的級別或級別。

+0

我沒有任何父母子女關係在我的表中。我如何創建一個 – 2014-10-10 08:36:06

+0

您有權訪問SCOTT模式嗎?如果你看員工表,你會明白什麼是必需的。 – 2014-10-10 08:38:49

+0

我知道如何創建一個層次結構,但在我的表中,第一列包含頂層節點,第二層包含第二層的節點,等等......我有五列,並且想要創建一個具有5個層次的樹。 – 2014-10-10 08:53:59