數據庫程序設計3 記錄 %ROWTYPE屬性 遊標

目錄

複合數據類型

PL/SQL  記錄

%ROWTYPE屬性

遊標

隱式遊標

顯示遊標

顯示遊標的屬性

遊標和for循環

帶參數的遊標

FOR UPDATE 子句


複合數據類型

複數據類型包括:

  • 記錄
  • 關聯數組(index by表)
  • 嵌套表
  • 可變長度數組

PL/SQL  記錄

和C++中的結構體比較像。

它是有幾個相關值構 成的複合變量,是表中單行數據結構的一個鏡像,可用於支持SELECT語句的返回值。記錄 將一行數據看成一個單元,而不是將每一列單獨處理 

定義

TYPE record_type IS RECORD  
    (   
        Variable_1 datatype1[,   
        Variable_2 datatype2[,   ...]]  
    ); 

注意這樣定義的是類型,還要再定義這個類型的變量。

例:

DECLARE  
    TYPE NewRecordTYPE IS RECORD  
    (   
        id number,
        name varchar2(10)  
    );  
    recTest NEWRECORDTYPE;    
BEGIN  
    SELECT empno,ename INTO recTest    
        FROM emp WHERE empno=7369;  
    DBMS_OUTPUT.PUT_LINE  
        (recTest.id||'號員工的姓名是'||recTest.name);    
END;

%ROWTYPE屬性

聲明的變量對應於數據庫表或視圖中列的集合。在%ROWTYPE之前加上數據庫表名。字段表示表中的列。

這種數據類型可以一個變量把整個表的東西讀出來,用".元素名"使用。

DECLEAR 
    emp_rec    emp%rowtype;
BEGIN
    select * into emp_rec
    from emp
    where empno=7788;

    INSERT INTO test VALUES 
        (emp_rec.EMPNO,emp_rec.ENAME,...,)
    commit;
END;

遊標

遊標是一種PL/SQL控制結構,可以對SQL語句 的處理進行顯式控制,便於對遊標的行數據逐條進行處理。 
分爲隱式遊標顯式遊標。

例如刪除數據時刪除掉多少行數據,就通過隱式遊標來獲得。

隱式遊標

從EMP中刪除指定部門,返回刪除的行的數量。

DECLARE
    v_deptno    NUMBER := 20;
    v_rows_deleted    VARCHAR2(30);
BEGIN
    DELETE FROM emp
    WHERE deptno = v_deptno;
    v_rows_deleted := SQL%ROWCOUNT;
    dbms_output.put_line(v_rows_deleteed || 'rows deleted.');
END;

顯示遊標

需要自己定義打開顯示關閉。

理解:遊標存在指針,從剛開始指向第一條,逐漸移動來遍歷結果集。

操作:

  • 定義遊標
  • 打開遊標
  • 提取遊標
  • 關閉遊標

注意:一點特殊的是,遍歷到的結果集不能再取了,即只能順着遍歷,不能倒回來看。

聲明

CURSOR cur_name IS 
    select statement

打開遊標

OPEN cur_name

提取遊標

FETCH cur_name INTO [variable1,variable2,...]

關閉遊標

關閉遊標釋放佔用的內存空間,不寫也是不出問題的。

CLOSE cur_name

例子:

DECLARE
    v_ename    emp.name%TYPE;
    v_sal    emp.sal%TYPE;
    CURSOR    cur_emp    IS
        select ename,sal
        from emp
        where sal>2000;
BEGIN
    OPEN cur_emp;
    FETCH cur_emp INTO v_ename,v_sal;
    dbms_output.putline(v_ename || ' ' || v_sal);
    FETCH cur_emp INTO v_ename,v_sal;
    dbms_output.put_line(v_ename || ' ' || v_sal;
    CLOSE cur_emp;
END;

顯示遊標的屬性

屬性 類型 描述
%ISOPEN bool 遊標打開的爲TRUE
%NOTFOUND bool FETCH語句沒有返回數據是TRUE
%FOUND bool FETCH返回一行記錄則爲TRUE
%ROWCOUNT 數值 返回到現在爲止從遊標中取出的記錄數目

例子

DECLARE
    v_ename    emp.name%TYPE;
    v_sal    emp.sal%TYPE;
    CURSOR    cur_emp    IS
        select ename,sal
        from emp
        where sal>2000;
BEGIN
    IF NOT cur_emp%ISOPEN THEN
        OPEN cur_emp;
    END IF;
    LOOP
        FETCH cur_emp INTO v_ename,v_sal;
        EXIT WHEN cur_emp%NOTFOUND;
        dbms_output.putline(cur_emp%ROWCOUNT);
        dbms_output.put_line(v_ename || ' ' || v_sal);
    END LOOP;
    CLOSE cur_emp;
END;

遊標和for循環

  • 遊標式的for循環可以方便的處理顯示遊標。
  • 隱式的打開提取和關閉遊標。
  • 隱式聲明記錄類型變量。
DECLARE 
    CURSOR emp_cursor IS
        SELECT empno,ename FROM emp;
BEGIN
    FOR emp_record IN emp_cursor LOOP
        dbms_opyput.putline(emp_record.empno);
    END LOOP;
END;

帶參數的遊標

每次傳入不同值可以獲得不同的結果集。更靈活

DECLARE
    CURSOR    cur_emp (p_sal NUMBER)    IS
        select ename,sal
        from emp
        where sal>2000;
BEGIN
    FOR rec_emp IN cur_emp(2000) LOOP
        dbms_output.put_line(v_ename || ' ' || v_sal);
    END LOOP;
END;

簡單循環 

DECLARE
    CURSOR    cur_emp (p_sal NUMBER)    IS
        select ename,sal
        from emp
        where sal>2000;
    rec_emp cur_emp%ROWTYPE
BEGIN
    OPEN cur_emp(3000);
    LOOP
        FETCH cur_emp INTO rec_emp;
        EXIT when cur_emp%NOTFOUND;
        dbms_output.put_line(v_ename || ' ' || v_sal);
    END LOOP;
    CLOSE cur_emp;
END;

FOR UPDATE 子句

用遊標對結果集進行修改。期間需要加鎖以拒絕訪問。

語法

SELECT ...
FROM ...
FOR UPDATE [OF column_reference][NOWAIT];

noway表示其他請求無需等待,直接返回錯誤。

SELECT *
FROM emp
WHERE empno=7788
FOR UPDATE nowait;

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章