2012-01-09 47 views
0

PL/SQL我想用一個前 - 後模式方法與PL/SQL(僞代碼)前,後點模式

模式的方法:

procedure doIt(DO_SOMETHING) 
is 
    l_cnt      pls_integer := 1; 
begin 
    loop 
     begin 
     DO_SOMETHING; 
     exit; 

     exception 
     when exception changed then 
      if l_cnt = 2 then 
      --raise exception... 
      else 
      l_cnt := l_cnt + 1; 
      end if; 
     end; 
    end loop; 
end; 

並執行它像這樣的:

begin 
    doIt(execute immediate sql_statement using in or out); 
end; 

正如你可以看到,我想用不同的動態SQL語句,但總是相同的前,後圖案的方法(與進出變量的一個或多個立即執行)。

有人想法我怎麼能解決這個問題?

+0

我不熟悉之前/之後的模式。循環和櫃檯是什麼? – Rene 2012-01-09 11:30:23

+1

所以你想讓用戶執行DO_SOMETHING中的內容?如果選擇,他們將需要一個返回的遊標,如果有任何DML/DDL或任何開放式結束,這是一個非常可怕的方法imo – tbone 2012-01-09 12:10:06

回答

1

這個解決方案不是很好,但它的工作原理。也許你可以從它開始,創造更好的東西:
我使用中的doIt 2個參數功能 -
1)要執行的命令立即
2)參數爲ANYDATA類型
在執行立即命令我」我把把anydata轉換成我創建的某種類型的所有邏輯來包裝IN OUT參數。

這裏是代碼:

一種像這樣應該爲每個不同的命令來創建:

create or replace type some_type as object(a number, b number); 
/

這是程序:

create or replace procedure doIt(aa in varchar2, param IN OUT anydata) is 
begin 
    execute immediate aa using in out param; 
end doIt; 
/

,這是我怎麼稱呼它(在這個例子中,我只是選擇從雙數到一些OUT參數的計數(*)):

declare 
    i number; 
    prm some_type; 
    ad anydata; 
    a number; 
    b number; 
begin 

    prm := new some_type(a,b); 
    ad := anydata.convertobject(prm); 

    doIt('declare prmAd anydata := :0; prm1 some_type; x number; begin x := prmAd.getobject(prm1); select count(*) into prm1.a from dual; :0 := anydata.convertobject(prm1); end;', ad); 

    i := ad.GetObject(prm); 
    dbms_output.put_line(prm.a); 
end; 

基本上,你可以添加到doIt程序,你想要什麼,並運行它的任何命令。

我想你可以做的事情 - 將一些立即執行的字符串移動到doIt過程中,也許可以更好地聲明類型等等。

+0

非常感謝。我會嘗試你的建議。 – maveonair 2012-01-12 12:29:43

0

我找不到以前好多資料/模式之後,但在看你的努力去實現它可能是這個樣子:

create or replace 
procedure doIt(stmt in varchar2, param in varchar2) 
is 
    l_cnt pls_integer := 1; 
begin 
    loop 
     begin 
     execute immediate stmt using param; 
     exit; 

     exception 
     when others then 
      if l_cnt = 2 then 
      raise; 
      else 
      l_cnt := l_cnt + 1; 
      end if; 
     end; 
    end loop; 
end; 
/

-- run it 
exec doIt('insert into my_table (col1) values (:val1)', 'richard'); 

這裏的問題是,如果你想傳遞兩個參數那麼你將不得不重寫'doIt',例如:

procedure doIt(stmt in varchar2, param1 in varchar2, param2 in varchar2) 
... 
using param1, param2 

另外,另一個警告是將不同的數據類型傳遞給參數。您可以再次使用正確的數據類型覆蓋該過程 - 警告這可能會讓多個數據類型或參數個數變得混亂。