Oracle层次查询技巧create table emp_hire asselectempno,mgr,ename from empselect * from emp_hire
| EMPNO | MGR | ENAME |
| 5555 | 7900 | ggg |
| 7369 | 7902 | SMITH |
| 7499 | 7698 | ALLEN |
| 7521 | 7698 | WARD |
| 7566 | 7839 | JONES |
| 7654 | 7698 | MA & RTIN |
| 7698 | 7839 | BLAKE |
| 7782 | 7839 | CLARK |
| 7788 | 7566 | SCOTT |
| 7839 | KING |
| 7844 | 7698 | TURNER |
| 7900 | 7698 | JAMES |
| 7902 | 7566 | FORD |
| 7934 | 7782 | MILLER |
| 7876 | 7788 | ADAMS |
这些数据存在着层次关系select lpad("*",level,"*")||e.ename ename, e.empno, mgr fa_id, (select ename from emp_hire where empno=e.mgr) fa_namefrom emp_hiree START WITH MGR IS NULL CONNECT BY PRIOR EMPNO = MGR
| ENAME | EMPNO | FA_ID | FA_NAME |
| *KING | 7839 |
| **JONES | 7566 | 7839 | KING |
| ***SCOTT | 7788 | 7566 | JONES |
| ****ADAMS | 7876 | 7788 | SCOTT |
| ***FORD | 7902 | 7566 | JONES |
| ****SMITH | 7369 | 7902 | FORD |
| **BLAKE | 7698 | 7839 | KING |
| ***ALLEN | 7499 | 7698 | BLAKE |
| ***WARD | 7521 | 7698 | BLAKE |
| ***MA & RTIN | 7654 | 7698 | BLAKE |
| ***TURNER | 7844 | 7698 | BLAKE |
| ***JAMES | 7900 | 7698 | BLAKE |
| ****ggg | 5555 | 7900 | JAMES |
| **CLARK | 7782 | 7839 | KING |
| ***MILLER | 7934 | 7782 | CLARK |
其中start with -- this identifies all LEVEL=1 nodes in the tree connect by -- describes how to walk from the parent nodes above to their children and their childrens children. 层次是一棵树, 又如同一个家族图谱 每一个子节电只有一个父节点;每一个分支,最末端是叶节点; SELECT ename Employee, CONNECT_BY_ISLEAF IsLeaf,LEVEL lev, SYS_CONNECT_BY_PATH(ename, "/") PathFROM emp START WITH MGR IS NULL CONNECT BY PRIOR EMPNO = MGR
| EMPLOYEE | ISLEAF | LEV | PATH |
| KING | 0 | 1 | /KING |
| JONES | 0 | 2 | /KING/JONES |
| SCOTT | 0 | 3 | /KING/JONES/SCOTT |
| ADAMS | 1 | 4 | /KING/JONES/SCOTT/ADAMS |
| FORD | 0 | 3 | /KING/JONES/FORD |
| SMITH | 1 | 4 | /KING/JONES/FORD/SMITH |
| BLAKE | 0 | 2 | /KING/BLAKE |
| ALLEN | 1 | 3 | /KING/BLAKE/ALLEN |
| WARD | 1 | 3 | /KING/BLAKE/WARD |
| MA & RTIN | 1 | 3 | /KING/BLAKE/MA & RTIN |
| TURNER | 1 | 3 | /KING/BLAKE/TURNER |
| JAMES | 0 | 3 | /KING/BLAKE/JAMES |
| ggg | 1 | 4 | /KING/BLAKE/JAMES/ggg |
| CLARK | 0 | 2 | /KING/CLARK |
| MILLER | 1 | 3 | /KING/CLARK/MILLER |
检查一个层次是否存在闭循环CONNECT_BY_ISCYCLE 找出根节点CONNECT_BY_ROOT SELECT ename Employee, CONNECT_BY_ISCYCLE,CONNECT_BY_ROOT ename FROM emp START WITH MGR IS NULL CONNECT BY NOCYCLE PRIOR EMPNO = MGR
| EMPLOYEE | CONNECT_BY_ISCYCLE | CONNECT_BY_ROOTENAME |
| KING | 0 | KING |
| JONES | 0 | KING |
| SCOTT | 0 | KING |
| ADAMS | 0 | KING |
| FORD | 0 | KING |
| SMITH | 0 | KING |
| BLAKE | 0 | KING |
| ALLEN | 0 | KING |
| WARD | 0 | KING |
| MA & RTIN | 0 | KING |
| TURNER | 0 | KING |
| JAMES | 0 | KING |
| ggg | 0 | KING |
| CLARK | 0 | KING |
| MILLER | 0 | KING |
层次查询的过滤条件SELECT ename Employee, CONNECT_BY_ISLEAF IsLeaf,LEVEL lev, SYS_CONNECT_BY_PATH(ename, "/") PathFROM empwhere level<3 START WITH MGR IS NULL CONNECT BY PRIOR EMPNO = MGR
Restriction on LEVEL in WHERE Clauses In a [NOT] IN condition in a WHERE clause, if the right-hand side of the condition is asubquery, you cannot use LEVEL on the left-hand sideof the condition. However, you can specify LEVEL in a subquery of the FROM clause to achieve the same result. For example, thefollowing statement is not valid: SELECT employee_id, last_name FROM employeesWHERE (employee_id,LEVEL)IN (SELECTemployee_id, 2 FROM employees)START WITHemployee_id = 2CONNECT BY PRIORemployee_id = manager_id;But the following statement is valid because it encapsulates the querycontaining theLEVEL information in the FROM clause: SELECT v.employee_id, v.last_name, v.levFROM(SELECT employee_id,last_name, LEVEL levFROM employees vSTART WITHemployee_id = 100CONNECT BY PRIORemployee_id = manager_id) vWHERE(v.employee_id, v.lev) IN(SELECT employee_id,2 FROM employees);
SIBLINGS的排序 SELECT ename Employee, CONNECT_BY_ISLEAF IsLeaf,LEVEL lev, SYS_CONNECT_BY_PATH(ename, "/") PathFROM emp START WITH MGR IS NULL CONNECT BY PRIOR EMPNO = MGRORDER SIBLINGS BY ename desc
| EMPLOYEE | ISLEAF | LEV | PATH |
| KING | 0 | 1 | /KING |
| JONES | 0 | 2 | /KING/JONES |
| SCOTT | 0 | 3 | /KING/JONES/SCOTT |
| ADAMS | 1 | 4 | /KING/JONES/SCOTT/ADAMS |
| FORD | 0 | 3 | /KING/JONES/FORD |
| SMITH | 1 | 4 | /KING/JONES/FORD/SMITH |
| CLARK | 0 | 2 | /KING/CLARK |
| MILLER | 1 | 3 | /KING/CLARK/MILLER |
| BLAKE | 0 | 2 | /KING/BLAKE |
| WARD | 1 | 3 | /KING/BLAKE/WARD |
| TURNER | 1 | 3 | /KING/BLAKE/TURNER |
| MA & RTIN | 1 | 3 | /KING/BLAKE/MA & RTIN |
| JAMES | 0 | 3 | /KING/BLAKE/JAMES |
| ggg | 1 | 4 | /KING/BLAKE/JAMES/ggg |
| ALLEN | 1 | 3 | /KING/BLAKE/ALLEN |
注意:
ORDER SIBLINGS By一定与start with 与 connect by一起使用
Oracle解析流程详解Oracle数据块体系介绍相关资讯 Oracle基础教程
- Oracle块编程返回结果集详解 (11/10/2013 10:45:58)
- Oracle基础教程之设置系统全局区 (08/22/2013 14:24:00)
- Oracle基础教程知识点总结 (06/18/2013 07:43:32)
| - Oracle基础教程之tkprof程序详解 (10/22/2013 11:49:50)
- Oracle基础教程之sqlplus汉字乱码 (07/18/2013 16:30:00)
- Oracle 管理之 Linux 网络基础 (02/16/2013 18:37:35)
|
本文评论 查看全部评论 (0)