今日はかなり神秘的な問題に遭遇しました。私は次のパラメータを使用して(パラメータの一つが0に等しいとき、私から定義された例外を発生させなければならない)私のSQL関数f_interestrate()
を実行したよう:SQL:関数内での例外処理
:ORA-06503: PL/SQL: Function returned without value
ORA-06512: at "NOAHBASE.GENERAL_FUNCTIONS", line 73
06503. 00000 - "PL/SQL: Function returned without value"
*Cause: A call to PL/SQL function completed, but no RETURN statement was executed.
*Action: Rewrite PL/SQL function, making sure that it always returns a value of a proper type.
SELECT GENERAL_FUNCTIONS.F_INTERESTRATE(2500000, 0.10, 0) FROM dual;
は私に次のエラーを与えました
しかし、次のコードサンプルで見られるように、関数は代わりに私が定義した例外ex_invalid_devisor
のフォームを呼び出す必要があります。この関数はパッケージ内にネストされていることに注意してください。
FUNCTION f_interestrate(pn_principal NUMBER, pn_interest NUMBER, pn_years NUMBER) RETURN NUMBER IS
vn_interestrate NUMBER;
ex_invalid_devisor EXCEPTION;
BEGIN
IF pn_principal = 0 OR
pn_interest = 0 OR
pn_years = 0 THEN
RAISE ex_invalid_devisor;
ELSE
vn_interestrate := ((pn_interest/pn_principal)-1)/pn_years;
RETURN vn_interestrate;
END IF;
EXCEPTION
WHEN ex_invalid_devisor THEN
DBMS_OUTPUT.PUT_LINE('Devisor must be bigger then 0');
END;
何か間違っていますか?
例外が発生した場合には、 'return'句がありません。あなたは、例えばを置く必要があります。 catchブロックに 'nullを返す 'か、例外を再発生させる。あなたの現在のブロックはそれを静かに呑み込む –
あなたの手続きは例外を発生させ、メッセージを出力するためにエラーを処理しますが、この場合戻り値はありません – Aleksej
はい、あなたは何か間違っている:あなたの例外ブロックは何もしません。関数では、エラーを発生させる必要があります(ユーザー定義のエラーの場合は、RAISE_APPLICATION_ERRORを使用して特定のエラー・メッセージを出力できます)。また、DBMS_OUTPUTを使用する必要がある場合は、デバッグ目的でのみ使用する必要があります(IMHO)。プロダクションコードには場所がありません。個人的には、デバッグの他の方法と一緒に行こうと思います。アクションが発生したかどうかを記録する必要がある場合は、代わりにテーブルにログを記録してください。 – Boneist