1. 程式人生 > >oracle中用start with...connect by prior子句實現遞迴查詢[例子不錯]

oracle中用start with...connect by prior子句實現遞迴查詢[例子不錯]

  今天在做許可權這一塊,碰到要讀取oracle中的樹形結構,所以就用到了start with...connect by prior。所以留個腳印以後碰到可以看看。

  在oracle中的select語句可以用start with...connect by prior子句實現遞迴查詢,connect by 是結構化查詢中用到的,其基本語法是:

//如果只用connect by 而不加 prior 查詢的將是 level 為1的一級。
select ... from tablename start with cond1 
connect by prior cond2 
where cond3; 

這裡的where是不能加的,我一加一個where就報 sql命令未正確結束的錯誤。如果有人可以加上去使用,那也請高手我下吧。本人先謝謝了。

不過可以先寫 where 然後使用 connect by prior  例如:select * from Sysfunction where nodetype='4' start with parentid ='123'(值) connect by prior functionid=parentid order by level(關鍵字:級別),parentid, funorder;

簡單說來是將一個樹狀結構儲存在一張表裡,比如一個表中存在兩個欄位: 
id,parentid那麼通過表示每一條記錄的parent是誰,就可以形成一個樹狀結構。 

用上述語法的查詢可以取得這棵樹的所有記錄。 

其中cond1 是根結點的限定語句,當然可以放寬限定條件,以取得多個根結點,實際就是多棵樹。 

cond2是連線條件,其中用prior表示上一條記錄

,比如 connect by prior id=parentid就是說上一條記錄的ID是本條記錄的parentid,即本記錄的父親是上一條記錄。 
cond3是過濾條件,用於對返回的所有記錄進行過濾。 

對於oracle進行簡單樹查詢(遞迴查詢) 
deptid      paredeptid   name 
number    number        char (40 Byte) 
部門id 父部門id(所屬部門id) 部門名稱 
通過子節點向根節點追朔.

複習一下:start with ...connect by 的用法, start with 後面所跟的就是就是遞迴的種子。 

遞迴的種子也就是遞迴開始的地方 connect by 後面的"prior" 如果預設:則只能查詢到符合條件的起始行,並不進行遞迴查詢; 

connect by prior 後面所放的欄位是有關係的,它指明瞭查詢的方向。

下面看下幾個例子:


create table automobiles(
       part_id number(5)
         constraint pk_auto_part_id primary key,
       parent_id number(5)
         constraint fk_auto_ppid_ references  automobiles(part_id),
       part_cname varchar2(30) not null,
       part_ename varchar2(30) not null,
       mp_cost number(9,2),
       desribe varchar2(20)    
);

--插入資料
insert into automobiles values( 1,null,'汽車','mobile',84321.99,'Assembly');
insert into automobiles values( 2,1,'車身','bodywork',19892.99,'Manufacture');
insert into automobiles values( 3,1,'傳送機','engine',42128,'Purchase');
insert into automobiles values( 4,1,'附件','attached',15212,'Assembly');
insert into automobiles values( 5,2,'保險槓','bumper',4812.95,'Purchase');
insert into automobiles values( 6,2,'底盤','chassis',12795.11,'Manufacture');
insert into automobiles values( 7,2,'行李箱','Boot',812.11,'Manufacture');
--分層sql指令碼語句練習
select level,part_id,parent_id,part_cname,part_ename,mp_cost,desribe
from automobiles
start with part_id=1
connect by prior part_id=parent_id 
order by level;
--縮排顯示
select level,
    lpad(' ',2*level-1)||part_cname||' '||part_ename as partName
from automobiles
start with part_id=1
connect by prior part_id=parent_id
order by level;
--使用子查詢  當然也可以在from中加入條件來達到子查詢的效果
select level,lpad(' ',2*level-1)||part_cname||' '||part_ename as partName from automobiles
start with part_id=(select part_id from automobiles where part_cname like '%軸%')
connect by prior  part_id=parent_id
order by level;
--自底向上的遍歷
select level,lpad(' ',2*level-1)||part_cname||' '||part_ename as partName
from automobiles
start with part_id=(select part_id from automobiles where part_cname like '%軸%')
connect by prior parent_id=part_id
order by level;
--刪除指定的節點
select level,lpad(' ',2*level-1)||part_cname||' '||part_ename as partName from automobiles
where part_cname <> '底盤'
start with part_id=1
connect by prior parent_id=part_id
order by level;
--刪除分支
select level,lpad(' ',2*level-1)||part_cname||' '||part_ename as partName from automobiles
start with part_id=1
connect by prior parent_id=part_id and part_cname <> '底盤'
order by level;