顯式游標是處理多行查詢結果的標準機制,提供對結果集的精確控制。本文系統講解游標完整生命週期操作,從宣告到關閉的每個關鍵步驟。
CURSOR cursor_name IS select_statement;
關鍵規則:
*全選DECLARE
CURSOR c_emp IS
SELECT empno, ename, salary
FROM emp
WHERE salary > 2000
ORDER BY ename;
BEGIN
-- 游標操作邏輯
END;
OPEN cursor_name;
執行查詢、建立結果集、將指標定位在第一行之前。若查詢涉及變數綁定,以OPEN時刻的變數值為準。
FETCH cursor_name INTO variable[, variable,...];
核心規則:
SET SERVEROUTPUT ON
DECLARE
v_ename EMP.ENAME%TYPE;
v_salary EMP.SALARY%TYPE;
CURSOR c_emp IS SELECT ename, salary FROM emp;
BEGIN
OPEN c_emp;
FETCH c_emp INTO v_ename, v_salary;
DBMS_OUTPUT.PUT_LINE('Salary of Employee ' || v_ename || ' is ' || v_salary);
-- 重複FETCH獲取後續行...
CLOSE c_emp;
END;
手工重複FETCH程式碼冗長難維護,標準模式採用LOOP + FETCH + EXIT WHEN:
SET SERVEROUTPUT ON
DECLARE
v_ename EMP.ENAME%TYPE;
v_salary EMP.SALARY%TYPE;
CURSOR c_emp IS SELECT ename, salary FROM emp;
BEGIN
OPEN c_emp;
LOOP
FETCH c_emp INTO v_ename, v_salary;
EXIT WHEN c_emp%NOTFOUND; -- 關鍵:游標屬性判斷結束
DBMS_OUTPUT.PUT_LINE('Salary of Employee ' || v_ename || ' is ' || v_salary);
END LOOP;
CLOSE c_emp;
END;
CLOSE cursor_name;
最佳實踐:
cursor_name%ISOPEN檢查狀態後再關閉| 技巧 | 說明 | 適用場景 |
|---|---|---|
| 參數化游標 | CURSOR c(p_deptno NUMBER) IS ... | 同一查詢邏輯,不同參數多次執行 |
| FOR UPDATE鎖定 | SELECT ... FOR UPDATE [OF col] [NOWAIT] | 後續需UPDATE/DELETE當前行 |
| WHERE CURRENT OF | UPDATE ... WHERE CURRENT OF cursor_name | 避免重複WHERE條件,精準定位當前行 |
| BULK COLLECT | 批量提取至集合,減少上下文切換 | 大量資料處理(>1000行) |
| 游標變數 | TYPE ref_cur IS REF CURSOR; | 動態SQL、跨程序傳遞結果集 |
掌握顯式游標完整生命週期操作,是PL/SQL程式設計的基本功。實務中建議:統一採用迴圈化提取模式、嚴格管理游標開關、善用參數化與FOR UPDATE機制、大數據量場景引入BULK COLLECT優化。