Javaでinstanceofを持っているように、pl_sql関数で入力パラメータのデータ型を決定する方法はありますか? ダンプ機能を使用してみましたが、クエリでのみ使用できます。
1 に答える
where
コメントから、入力パラメーターをループして動的クエリ文字列を作成し、おそらく手動で入力することなく句を作成したいようです。それは、メンテナンスと理解を難しくし、あまりメリットがないように思われます。
ただし、演習として、ビューからパラメーター定義をループできuser_arguments
ます。問題は、名前を付けないと実際のパラメーター値を取得できないことです。その場合、値を直接動的文字列に入れる場合にのみデータ型が問題になります (これは実際にはループでは実行できません)。バインド変数としてではなく、とにかく行うのは悪いことです。また、バインド変数を使用している場合は、データ型を知る必要はありません。
したがって、主に私自身の娯楽のために、さまざまなデータ型のテーブルがある場合:
create table t42(col1 varchar2(10), col2 number, col3 date);
insert into t42 values ('data', 42, trunc(sysdate));
...そして、パラメーター名がテーブルの列名と一致する関数を使用すると、バインド変数を使用して動的文字列を作成できます。
create function f42(col1 t42.col1%type, col2 t42.col2%type,
col3 t42.col3%type)
return varchar2 is
str varchar(4000);
result t42.col1%type;
have_where boolean := false;
begin
str := 'select col1 from t42';
for r in (
select argument_name, data_type
from user_arguments
where object_name = 'F42'
and position > 0 -- to account for return type
order by position
) loop
if not have_where then
have_where := true;
str := str || ' where ';
else
str := str || ' and ';
end if;
str := str || r.argument_name || ' = :' || r.argument_name;
end loop;
dbms_output.put_line(str);
execute immediate str into result using col1, col2, col3;
return result;
end;
/
次に、SQL*Plus から呼び出すことができます。
SQL> var rc varchar2(10);
SQL> exec :rc := f42('data', 42, trunc(sysdate));
select col1 from t42 where COL1 = :COL1 and COL2 = :COL2 and COL3 = :COL3
PL/SQL procedure successfully completed.
SQL> print rc
RC
--------------------------------
data
明らかに非常に不自然な例ですが、using
すべてのパラメーターをリストする必要があるのは節だけで、より多くのパラメーターに対応できます。おもう。これは、これが良いアイデアだと思うという意味ではありません- ただの楽しみのために...
r.data_type
必要に応じて、値を確認することで、データ型に基づいてループ内で操作を行うことができます。
str := str || r.argument_name || ' = ';
if r.data_type = 'DATE' then
str := str || 'trunc(:' || r.argument_name || ')';
else
str := str || ':' || r.argument_name;
end if;
...呼び出しで値を指定せずに呼び出すことができtrunc
ます:
SQL> exec :rc := f42('data', 42, sysdate);
select col1 from t42 where COL1 = :COL1 and COL2 = :COL2 and COL3 = trunc(:COL3)
PL/SQL procedure successfully completed.
SQL> print rc
RC
--------------------------------
data
...しかし、それ以外は、動的文字列の各列の型を知る必要はありません。とにかくバインディングがそれを処理するからです。