2017-08-17 11 views
0

申し訳ありませんが、質問の名前が間違っています。より具体的な例をお伝えします。ループの各反復のデータを格納し、それらをすべて参照カーソルに戻しますか?

var1 VARCHAR(20); 
var2 VARCHAR(20); 

    --MYRECORD CONTAINS COLUMNS ELEMENT0, VAL 

    FOR MYRECORD IN EXPLICITCURSOR LOOP 
    SELECT COL1, COL2 INTO var1, var2 FROM table1 WHERE table1.COLUMNT=MYRECORD.VAL; 
    END LOOP; 

ご覧のとおり、私にはループがあり、その内側にはSELECTがあります。今、テストのために、私は毎回上書きされる2つの変数に結果を保存しています。 私は各反復(ELEMENT0、COL1、COL2)を保存する必要があり、REF CURSORを使って出力します。

EDIT1:私は、レコードタイプとレコードタイプを定義する可能性についてこの瞬間を見ています。誰かが私の場合の例を教えてもらえますか?出力パラメータとしてテーブルを設定する際に問題があります。 これは私がパッケージの冒頭で準備したものです。

TYPE my_record is RECORD(
    ELEMENT0  varchar2(20), 
    COL1   varchar2(20), 
    COL2   varchar2(20)); 

TYPE my_table IS TABLE OF my_record; 

と今の私は、このように私の手順については、OUTパラメータを使用しています:私はLOOPの各反復での私のOUTのparamの内側に私の3つのvarchar型の値を挿入しようとしている

TABLERESULT       OUT my_table 

この方法(値が正しくsettedされている):

INSERT INTO TABLERESULT(ELEMENT0,COL1,COL2) VALUES(ELEMENT0,COL1,COL2); 

、それは私にエラーを与える:

PL/SQL: ORA-00942: table or view does not exist 

このタイプのOUTパラメータを使用して何か間違っていますか?

提案がありますか?ありがとうございました。 (私はOracle 11gを使用しています)

EDIT2:@ APCの助けを借りて、命名エラーとコンパイラが問題を起こさないことがわかりました。私は続行し、私はあなたに知らせるでしょう。

+0

保存場所はどこですか?テーブル?ファイル? –

+0

"保存"とは、配列のようなものにこれらの3つのvarchar2値を格納し、それらのすべてをプロシージャ呼び出し元に参照カーソルで戻す方法が必要なことを意味します。あなたはそれを行う方法をアドバイスできますか? –

+0

一時テーブルに挿入しますか? –

答えて

0

レコード構造に一致するオブジェクトタイプを作成します。

これらのオブジェクト型のネストした表の型を作成します。

文字列の各タプレットに対して、配列に追加します。そして

次のようにカーソル変数を返す:表から選択FOR

OPENのCV(my_arrayで)を、 RETURN cv;

表関数は、配列をカーソル変数に割り当てることができる結果セットに変換します。これが必要なの反復なしで簡単に実現することができる。ここ https://livesql.oracle.com/apex/livesql/file/content_FFTOKNC4AHGPOQE79FF76S7EQ.html

CREATE OR REPLACE TYPE three_ot 
    AUTHID DEFINER IS OBJECT 
(
    element0 VARCHAR2 (200), 
    col1 VARCHAR2 (200), 
    col2 VARCHAR2 (200) 
) 
/

CREATE OR REPLACE TYPE three_nt IS TABLE OF three_ot 
/

CREATE OR REPLACE FUNCTION data_for_you 
    RETURN SYS_REFCURSOR 
    AUTHID DEFINER 
IS 
    l_cursor SYS_REFCURSOR; 
    l_nt  three_nt; 
BEGIN 
    SELECT three_ot (TO_CHAR (employee_id), last_name, first_name) 
    BULK COLLECT INTO l_nt 
    FROM hr.employees; 

    OPEN l_cursor FOR SELECT * FROM TABLE (l_nt); 

    RETURN l_cursor; 
END; 
/

DECLARE 
    l_cursor SYS_REFCURSOR := data_for_you(); 
    l_three three_ot; 
    element0 VARCHAR2 (200); 
    col1  VARCHAR2 (200); 
    col2  VARCHAR2 (200); 
BEGIN 
    LOOP 
     FETCH l_cursor INTO element0, col1, col2; 
     EXIT WHEN l_cursor%NOTFOUND; 
     DBMS_OUTPUT.put_line (col1); 
    END LOOP; 

    CLOSE l_cursor; 
END; 
/
+0

私はこの瞬間の私の編集で言ったように、私は最初の2つの点で問題があります。もしあなたが時間を見つけたら、それを達成する方法についてちょっと知っているのはすばらしいかもしれません。ありがとうございました。 –

0

は、ここでは、以下を参照してくださいコードを実行しますLiveSQLスクリプトへのリンクです。 スニペットの下に希望があります。私はこのコマンドを実行するためのワークスペースを持っていないので、任意の構文エラーを許してください。

--Wwhat i would suggest is rather going row-by-row this can be achieved by single iteration and can be returnedas ref cursor as output. 

DECLARE 
    lv sys.odcivarchar2list; 
    lv_ref sys_refcursor; 
BEGIN 
    SELECT val BULK COLLECT 
    INTO lv 
    FROM TABLE2; 

    OPEN lv_ref FOR SELECT * FROM TABLE1 WHERE TABLE1.COL IN 
    (SELECT COLUMN_VALUE FROM TABLE(lv) 
); 
END; 
/
+0

私は同意します。私の例では、ループの代わりにバルク収集も使用します。そして、あなたはTABLEから離れ、コレクションを参照するだけで済みます。その比較的最近の拡張にまだ調整していない。ニース! –

関連する問題