3

ストアド プロシージャを使用して、カーソルを使用してレコードを選択しています。このプロシージャは、レコード ID を入力として取得します。

コードは次のとおりです。

create or replace
procedure GET_ITEM_DETAILS_ALL
(
  cur_out out sys_refcursor,
  PSTRING VARCHAR2 DEFAULT NULL
)
is
  query_string  VARCHAR2(1000);
Begin
  query_string := 'Select IT.SL_NO from ITEM_DETAILS IT where IT.SL_NO in (:sl) order by IT.SL_NO';
  OPEN cur_out FOR query_string USING PSTRING;
End;

プロシージャの呼び出し/テストには、以下のコードを使用します。

VAR R REFCURSOR
EXEC GET_ITEM_DETAILS_ALL (:R, '4')
PRINT R 

問題は、'4' や '2' などの単一の整数を渡すとプロシージャがデータを返しますが、'1,2' または '3,4' を渡すとエラーが表示されることです。

4

4 に答える 4

2
   OPEN cur_out FOR Select IT.SL_NO from ITEM_DETAILS IT where IT.SL_NO in (SELECT REGEXP_SUBSTR(sl,'[^,]+', 1, LEVEL) FROM DUAL CONNECT BY REGEXP_SUBSTR(sl, '[^,]+', 1, LEVEL) IS NOT NULL ) order by IT.SL_NO
于 2015-12-31T06:14:16.740 に答える
0

問題は、PSTRING が配列ではなく単一の変数であることです。したがって、あなたのステートメントは実際には

.... where IT.SL_NO = PSTRING

パスすると機能し、パスした4ところで失敗するのはそのためです1,2

このように動的 SQL を使用しても意味がありません (文字列を使用せずに ref カーソルを開くことができます)。ただし、動的 ​​SQL を利用することは、問題を解決する 1 つの方法です。

query_string := 'Select IT.SL_NO from ITEM_DETAILS IT where IT.SL_NO in ('
                   ||PSTRING||
                   ') order by IT.SL_NO';
OPEN cur_out FOR query_string;

または、文字列トークナイザーを使用して、文字列をトークンに変換することもできます。残念ながら、Oracle には標準のビルトインはありませんが、データベースのバージョンごとにさまざまな回避策があります。Adrian Billington が彼のサイトで良いまとめをしています。これらのアプローチのいずれかを使用すると、動的 SQL を捨てることができます。

OPEN cur_out FOR select IT.SL_NO from ITEM_DETAILS IT 
   where IT.SL_NO in ( select * from table ( your_string_tokenizer( PSTRING ) ) ) 
   order by IT.SL_NO;
于 2013-03-03T09:27:53.170 に答える
0

解決策を以下に示します。

create or replace procedure GETITEM_DETAILS_ALL

(
    cur_out out sys_refcursor,
    PSTRING VARCHAR2 DEFAULT NULL
 )

is

query_string  VARCHAR2(1000);

Begin

query_string := 'Select IT.SL_NO from ITEM_DETAILS IT where IT.SL_NO in (' || PSTRING || ') order by IT.SL_NO';

OPEN cur_out FOR query_string;

End;
于 2013-03-03T12:15:38.290 に答える
0

1 つのバインド変数を使用して値のリストをクエリに渡すことはできません。
カンマ区切りのリストで文字列を渡すと、クエリは
Select IT.SL_NO from ITEM_DETAILS IT where IT.SL_NO in ('1,2') order by IT.SL_NO
どちらが正しくなくなります。
入力文字列をクエリ内の値のリストに手動で変換する必要があります。

于 2013-03-03T09:12:16.957 に答える