2012-09-27 59 views
0

我試圖做一些事情,如:有沒有辦法重新啓動遊標?甲骨文

for(int i = 0; i<10; i++) 
{ 
    for(int j = 0; j<10; j++) 
    { 
     Blah; 
    } 
} 

//As you can see each time that there is a different i, j starts at 0 again. 

在Oracle中使用遊標。但如果我是正確的,在從遊標獲取所有行後,它將不會重新啓動。有沒有辦法做到這一點?

這裏是我的SQL:

CREATE OR REPLACE PROCEDURE SSACHDEV.SyncTeleappWithClientinfo 
as 
teleCase NUMBER; 

CURSOR TeleAppCursor 
is 
    Select 
     distinct(casenbr) 
    from TeleApp; 


CURSOR ClientInfoCursor 
is 
    Select casenbr 
    from clientinfo 
    where trim(cashwithappyn) is null; 

BEGIN 

    open TeleAppCursor; 
    open ClientInfoCursor; 

    LOOP 
     fetch TeleAppCursor into teleCase; 
     EXIT when TeleAppCursor%NOTFOUND; 

     LOOP 
      fetch ClientInfoCursor into clientCase; 
      EXIT when ClientInfoCursor%NOTFOUND; 
       if clientCase = teleCase then 

        update ClientInfo 
        set cashwithappyn = (select cashwithappyn from teleapp where casenbr = clientCase) 
        where casenbr = clientCase; 

        break; 
       end if; 
     END LOOP; 
    END LOOP; 

END; 

我沒有在網上查,是無法找到這樣的東西。

+1

首先,爲什麼「重新啓動」對你意味着什麼,你爲什麼需要「重新啓動」?您發佈的您想要完成的僞代碼似乎不需要重新啓動。其次,你爲什麼要在PL/SQL中編寫嵌套循環? SQL是一種基於集合的語言 - 編寫單個UPDATE語句會更有效率(更不用說更少的代碼),它可以更新要更新的每一行,而不是編寫兩個循環,併發布大量的' UPDATE'語句每個只更新一行。 –

+0

通過重新啓動我的意思是再次開始在結果表的頂部。 只有當caseNumber相同時,並且僅當第二張表cashwithappyn爲空時,我需要將第一張表的數據(cashwithappyn)輸入到第二張表中。 – Solid1Snake1

+1

我想,關閉光標,然後重新打開它會重新啓動光標。但是,我仍然同意Justin的觀點,你爲什麼想要在代碼中做所有的事情?它可以以更簡單的方式完成。 – Annjawn

回答

0

你不需要第二光標在所有的輸出,只是使用在Oracle中設置操作以更新相應的記錄,而無需手動搜索它們自己:

DECLARE 
    v_teleCase  TeleApp.teleCase%TYPE; 
    v_cashwithappyn TeleApp.cashwithappyn%TYPE 

    CURSOR TeleAppCursor 
    is 
     Select 
      distinct casenbr, cashwithappyn 
     from TeleApp; 

BEGIN 

    open TeleAppCursor; 

    LOOP 
     fetch TeleAppCursor into v_teleCase, v_cashwithappyn; 
     EXIT when TeleAppCursor%NOTFOUND; 

     UPDATE ClientInfo 
     SET cashwithappyn = v_cashwithappyn 
     WHERE casenbr = v_teleCase 
     AND trim(cashwithappyn) is null; 

    END LOOP; 

END; 

不建議使用與列名稱相同的變量。

2

您可以使用表變量來存儲sql語句的結果,然後循環遍歷表的任意次數,而不是重新啓動Cursor。

下面是使用SQL Fiddle Sample數據的示例。

DECLARE 
    CURSOR c1 IS 
     SELECT id, 
      TYPE, 
      details 
     FROM supportcontacts; 

    TYPE contactrec 
     IS TABLE OF c1%ROWTYPE INDEX BY BINARY_INTEGER; 

    acontact c1%ROWTYPE; 
    contactlist CONTACTREC; 
    counter  INTEGER; 
BEGIN 
    counter := 0; 

    OPEN c1; 

    LOOP 
     FETCH c1 INTO acontact; 

     IF c1%FOUND THEN 
      counter := counter + 1; 
     END IF; 

     Contactlist(counter) := acontact; 

     IF c1%NOTFOUND THEN 
      EXIT; 
     END IF; 
    END LOOP; 

    CLOSE c1; 



    FOR i IN 1..5 LOOP 
     FOR j IN 1..counter LOOP 
      dbms_output.Put_line(Contactlist(j).type || ' ' || Contactlist(j).details); 
     END LOOP; 
    END LOOP; 
END; 

/

其輸出

Email [email protected] 
Twitter @sqlfiddle 
Email [email protected] 
Twitter @sqlfiddle 
Email [email protected] 
Twitter @sqlfiddle 
Email [email protected] 
Twitter @sqlfiddle 
Email [email protected] 
Twitter @sqlfiddle 

這裏的SQL Fiddle但我無法弄清楚如何看到DBMS_OUTPUT

+0

查看您首先需要的輸出:SET SERVEROUTPUT ON – kurosch

+0

@kurosch在SQL小提琴中?你可以分享一個鏈接工作,因爲當[我嘗試](http://sqlfiddle.com/#!4/d41d8/2856),我得到了'ORA-00922:缺少或無效的選項:SET SERVEROUTPUT ON' –

+0

I我從來沒有使用SQL Fiddle,我不知道他們支持哪些選項。 – kurosch

相關問題