oracle ora-01001,ORA-01001 and ORACLE游标
為了處理sql語句,Oracle必須分配一片內存區域——上下文區域(context area),它包含了完成該處理所必需的信息, 其中包括語句要處理行的數目、 一個指向語句被分析以后產生的表示形式的指針, 以及查詢的活動集(active set 即查詢返回的行的集合)。
游標(cursor)是一個指向上下文區的句柄(handle)或指針。 通過游標, pl/sql程序可以控制上下文區和處理語句時上下文區發生什么
事情。
靜態游標, 顯式游標和隱式游標
顯式游標的處理包括四個pl/sql步驟,如下:
1)聲明游標。
2)為查詢打開游標。
3)將結果提取(fetch)到pl/sql變量中。
4)關閉游標。
游標聲明
對游標的聲明定義了游標的名字并將該游標和一個SELECT語句相關聯。
語法是:
CURSOR cursor_name IS SELECT_statement;
任何的SELECT 語句都是合法的,包括連接(join)和帶有UNION或MINUS子句的語句,但是不能包含INTO子句,游標的聲明可以在WHERE子句中引用pl/sql變量。這些變量被認為是聯編變量(bind variable,即已經被分配空間并映射到絕對地址的變量)
游標打開
當打開一個游標時會發生下面的事情:
a.聯編變量的取值被檢查。
b.根據聯編變量的取值,活動集被確定。
c.活動集的指針指向第一行。
在游標打開時刻并且僅僅在游標打開時刻對聯編變量進行檢查。
游標的屬性
在pl/sql中可以使用游標的四個屬性。pl/sql塊中,游標屬性附加在游標名的后邊。游標屬性返回的不是類型(如%type,%rowtype),它返回的是在表達式中可以使用的數值。這些屬性是%FOUND、%NOTFOUND、%ISOPEN、%ROWCOUNT。
a.%FOUND是一個布爾屬性。如果前一個FETCH語句返一個行,那么它的返回TRUE, 否則FALSE。如果在未打開游標以前就設置了%FOUND,那么回返回ora-1001(無效得游標)。
b.%NOTFOUND的行為方式與%FOUND正好相反。
c.%ISOPEN也是布爾屬性,用來確定相關的游標是否被打開了。
d.%ROWCOUNT此數字屬性返回目前為止由游標返回行的數目。如果在相關聯的游標還沒有打開或者已經關閉的時候進行引用,那么
也會返回ora-1001錯誤。
處理隱式游標
顯式游標用來處理返回多于一行的SELECT語句,但是所有的SQL語句在上下文區內部是可執行的,因此都有一個游標指向此上下文區。此游標就是所謂的“SQL 游標”(SQL cursor)。 與顯式游標不同的是, SQL游標不被程序打開和關閉。 pl/sql隱含地打開SQL游標,處理其中的SQL語句,然后關閉該游標。
隱式游標用于處理INSERT、UPDATE、DELETE和單行的SELECT..INTO語句。因為SQL 游標是通過pl/sql 引擎打開和關閉的,所以OPEN、FETCH、CLOSE命令是無關的。但是游標屬性(用SQL%..)可以被應用于SQL游標。
Ref:
eg:
CREATE OR REPLACE PROCEDURE OSM_DML_2SP.OSM_TAB_PROCPROC2(
ival IN OSM_TAB_PROC.COL_0%TYPE:=10,
ocnt IN OUT NUMBER)
AS
a OSM_TAB_PROC.COL_0%TYPE;
r OSM_TAB_PROC%ROWTYPE;
i NUMBER := 0;
CURSOR c1(ct0 NUMBER) IS SELECT COL_0 FROM OSM_DML_2SP.OSM_TAB_PROC WHERE COL_0>ct0;
BEGIN
IF c1%ISOPEN = FALSE THEN
OPEN c1(60);
END IF;
LOOP
EXIT WHEN c1%NOTFOUND; -- if cursor is not open used it ORA-01001 error
FETCH c1 INTO a;
SELECT * INTO r FROM OSM_DML_2SP.OSM_TAB_PROC WHERE COL_0=a AND ROWNUM<2;
r.COL_0 := a + ival;
r.COL_3 := TO_CHAR(a) || TO_CHAR(SYSDATE);
INSERT INTO OSM_DML_2SP.OSM_TAB_PROC VALUES r;
i := i + 1;
END LOOP;
CLOSE c1;
ocnt := i;
END;
DECLARE
cnt NUMBER := 0;
BEGIN
FOR i IN 1 .. 3 LOOP
OSM_DML_2SP.OSM_TAB_PROCPROC2(236*i,cnt);
EXECUTE IMMEDIATE 'INSERT INTO OSM_DML_2SP.OSM_TAB_PROC(COL_0) VALUES(:1)' USING cnt*i;
END LOOP;
END;
閱讀(6788) | 評論(0) | 轉發(0) |
總結
以上是生活随笔為你收集整理的oracle ora-01001,ORA-01001 and ORACLE游标的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: oracle随机备选数,Oracle查询
- 下一篇: oracle 10g gateway 安