カーソルを使用する例

TimesTenではカーソルがサポートされています。カーソルを使用して、SELECT文の結果セットを処理します。

「PL/SQLプログラムでのカーソルの使用」を参照してください。

この項で取り上げる例は次のとおりです。

これらの例で使用されるカーソル属性については、『Oracle Database PL/SQL言語リファレンス』明示的なカーソル属性を参照してください。

値のフェッチ

この項では、カーソルから値をフェッチする方法について、値をレコードにフェッチする方法も含めて、例を示します。

次の例では、カーソルを使用して、employees表から、department_idが30であるemployee_idおよびlast_nameを選択します。2つの変数が宣言され、カーソルからフェッチされた値を保持すると、FETCH文はループ内の行を1つずつ取得してすべての行を取得します。カーソルに残りの行がなくなると%NOTFOUNDカーソル属性が表示され、実行は停止します。

%NOTFOUNDは、INSERTUPDATE、またはDELETE文がどの行にも影響しなかったか、またはSELECT INTO文で行が戻されなかった場合にTRUEを生成します。

Command>  DECLARE
            CURSOR c_emp_cursor IS
              SELECT employee_id, last_name FROM employees
              WHERE department_id = 30;
            v_empno  employees.employee_id%TYPE;
            v_lname  employees.last_name%TYPE;
          BEGIN
            OPEN c_emp_cursor;
            LOOP
             FETCH c_emp_cursor INTO v_empno, v_lname;
            EXIT WHEN c_emp_cursor%NOTFOUND;
            DBMS_OUTPUT.PUT_LINE (v_empno || ' ' || v_lname);
            END LOOP;
            CLOSE c_emp_cursor;
          END;
          /

114 Raphaely
115 Khoo
116 Baida
117 Tobias
118 Himuro
119 Colmenares

次の例は前の例と似ており、同じ結果を返しますが、値をPL/SQLの変数ではなくPL/SQLのレコードにフェッチします。

Command> DECLARE
           CURSOR c_emp_cursor IS
             SELECT employee_id, last_name FROM employees
             WHERE department_id = 30;
           v_emp_record  c_emp_cursor%ROWTYPE;
         BEGIN
           OPEN c_emp_cursor;
           LOOP
             FETCH c_emp_cursor INTO v_emp_record;
           EXIT WHEN c_emp_cursor%NOTFOUND;
           DBMS_OUTPUT.PUT_LINE (v_emp_record.employee_id || ' ' |
             v_emp_record.last_name);
           END LOOP;
           CLOSE c_emp_cursor;
         END;
         /

114 Raphaely
115 Khoo
116 Baida
117 Tobias
118 Himuro
119 Colmenares
 
PL/SQL procedure successfully completed.

%ROWCOUNT属性および%NOTFOUND属性の使用

この例では、%ROWCOUNTカーソル属性、および前述の「値のフェッチ」の項にある例で示した%NOTFOUNDカーソル属性を使用する方法を示しています。%ROWCOUNTにより、INSERTUPDATEまたはDELETE文の影響を受けたかSELECT...INTOまたはFETCH...INTO文によって返された行の数が示されます。

Command> DECLARE
           CURSOR c_emp_cursor IS
             SELECT employee_id, last_name FROM employees
             WHERE department_id = 30;
           v_emp_record  c_emp_cursor%ROWTYPE;
         BEGIN
         OPEN c_emp_cursor;
         LOOP
           FETCH c_emp_cursor INTO v_emp_record;
           EXIT WHEN c_emp_cursor%ROWCOUNT > 10 OR c_emp_cursor%NOTFOUND;
           DBMS_OUTPUT.PUT_LINE (v_emp_record.employee_id || ' ' ||
             v_emp_record.last_name);
           END LOOP;
           CLOSE c_emp_cursor;
          END;
          /
114 Raphaely
115 Khoo
116 Baida
117 Tobias
118 Himuro
119 Colmenares
 
PL/SQL procedure successfully completed.

カーソルFORループの使用

TimesTenのPL/SQLでは、カーソルFORループがサポートされています。

最初の例では、PL/SQLは暗黙的にemp_recordを宣言します。OPEN文およびCLOSE文は必要ありません。結果は、前述の「%ROWCOUNT属性および%NOTFOUND属性の使用」の項にある例と同じです。

Command> DECLARE
           CURSOR c_emp_cursor IS
            SELECT employee_id, last_name FROM employees
            WHERE department_id = 30;
         BEGIN
           FOR emp_record IN c_emp_cursor
            LOOP
              DBMS_OUTPUT.PUT_LINE (emp_record.employee_id || ' ' ||
                 emp_record.last_name);
            END LOOP;
         END;
         /
114 Raphaely
115 Khoo
116 Baida
117 Tobias
118 Himuro
119 Colmenares
 
PL/SQL procedure successfully completed.

2番目の例では、副問合せを使用したFORループを示します。結果は、前の例、および前述の「%ROWCOUNT属性および%NOTFOUND属性の使用」の項にある例と同じです。

Command> BEGIN
          FOR emp_record IN (SELECT employee_id, last_name FROM
           employees WHERE department_id = 30)
          LOOP
            DBMS_OUTPUT.PUT_LINE (emp_record.employee_id || ' ' ||
              emp_record.last_name);
           END LOOP;
         END;
         /
114 Raphaely
115 Khoo
116 Baida
117 Tobias
118 Himuro
119 Colmenares
 
PL/SQL procedure successfully completed.