関数を作成します。

構文

CREATE [ OR REPLACE ] FUNCTION name [ (parameters) ]
  RETURN data_type
   [
          IMMUTABLE
        | STABLE
        | VOLATILE
        | DETERMINISTIC
        | [ NOT ] LEAKPROOF
        | CALLED ON NULL INPUT
        | RETURNS NULL ON NULL INPUT
        | STRICT
        | [ EXTERNAL ] SECURITY INVOKER
        | [ EXTERNAL ] SECURITY DEFINER
        | AUTHID DEFINER
        | AUTHID CURRENT_USER
        | PARALLEL { UNSAFE | RESTRICTED | SAFE }
        | COST execution_cost
        | ROWS result_rows
        | SET configuration_parameter
          { TO value | = value | FROM CURRENT }
   ...]
{ IS | AS }
    [ PRAGMA AUTONOMOUS_TRANSACTION; ]
    [ declarations ]
  BEGIN
    statements
  END [ name ];

説明

CREATE FUNCTION は関数を作成します。 CREATE OR REPLACE FUNCTION は、新しい関数を作成するか、既存の定義を置き換えます。

スキーマ名を指定すると、指定したスキーマで関数が作成されます。 指定しない場合、関数は現在のスキーマに作成されます。 新しい関数は、同じスキーマ内の同じ入力引数型を持つ既存の関数と同じ名前にすることはできません。 ただし、異なる入力引数型を持つ関数とであれば、名前を共有することができます。 これはオーバーロードと呼ばれます。 関数のオーバーロードは、Oracle と互換性のある PolarDB データベースの機能です。 格納されたスタンドアロン関数のオーバーロードは、Oracle データベースと互換性がありません。

既存の関数の定義を更新するには、CREATE OR REPLACE FUNCTION ステートメントを使用できます。 このステートメントを使用して関数の名前または引数型を変更することはできません。 使用した場合、新しい個別の関数が作成されます。 また、CREATE OR REPLACE FUNCTION ステートメントを使用して既存の関数の戻り値の型を変更することはできません。 既存の関数の戻り値の型を変更するには、関数を削除して、再度作成する必要があります。 OUT パラメーターを使用する場合、既存の関数を削除しない限り OUT パラメーターのタイプを変更することはできません。

関数を作成したユーザーが関数の所有者になります。

Oracle と互換性のある PolarDB データベースが関数のオーバーロードをサポートします。 入力 (IN、IN OUT) 引数のデータ型が異なる場合、種々の異なる関数に同じ名前を使用できます。

パラメーター

パラメーター 説明
name 関数の識別子。
parameters パラメーター値のリスト。
data_type 関数の RETURN ステートメントによって返される値のデータ型。
declarations 変数、カーソル、タイプ、またはサブプログラムの宣言。 サブプログラムの宣言が含まれる場合は、他のすべての変数、カーソル、およびタイプの宣言後に行う必要があります。
statements SPL プログラムステートメント。 BEGIN - END ブロックには、EXCEPTION セクションを含めることができます。
IMMUTABLE | STABLE | VOLATILE これらの属性を使って、クエリオプティマイザに関数の動作に関する情報を通知します。 いずれか 1 つのみを指定できます。 VOLATILE がデフォルト動作です。
  • IMMUTABLEは、関数はデータベースを変更することはなく、同じ引数値が指定されている場合は常に同じ結果を返すことを示します。 この関数が、データベース検索の実行または引数リストから除外されている情報の使用を行うことはありません。 この句が含まれている場合、すべて定数の引数を使った関数の呼び出しは、関数の値とすぐに置き換えることができます。
  • STABLE は、関数がデータベースを変更することはなく、一回のテーブルスキャンの間は関数が同じ引数値に対して同じ結果を返すことを示します。 この場合、SQL ステートメント間で結果が変わる可能性があります。 この属性は、データベース検索や、現在のタイムゾーンなどのパラメーター変数に依存する関数に適しています。
  • VOLATILE は、関数の値が一回のテーブルスキャンの間に変更されることを示します。 この場合、最適化は行えません。 結果が予測できたとしても、悪影響を及ぼす関数は 揮発性関数として分類する必要があることをご留意ください。 これにより、最適化が原因で呼び出しが取り消されるのを防ぎます。
DETERMINISTIC DETERMINISTIC は IMMUTABLE と同義です。 DETERMINISTIC 関数はデータベースを変更することはなく、同じ引数値が指定されている場合は常に同じ結果を返します。 この関数が、データベース検索の実行または引数リストから除外されている情報の使用を行うことはありません。 この句が含まれている場合、すべて定数の引数を使った関数の呼び出しは、関数の値とすぐに置き換えることができます。
[ NOT ] LEAKPROOF LEAKPROOF 関数が悪影響を及ぼすことはなく、関数の呼び出しに使用される値に関する情報は公開されません。
CALLED ON NULL INPUT | RETURNS NULL ON NULL INPUT | STRICT
  • CALLED ON NULL INPUT はデフォルト値です。 これは、一部の引数が NULL でも格納されているプロシージャが呼び出されることを示しています。 必要に応じて、作成者は NULL 値をチェックし、適切なレスポンスを行う責任があります。
  • RETURNS NULL ON NULL INPUT または STRICT は、一部の引数が NULL の場合は常に格納されているプロシージャが NULL を返すことを示します。 これらの句が指定されている場合、NULL 引数が存在するときは格納されているプロシージャは実行されません。 NULL が自動的に結果として返されます。
[ EXTERNAL ] SECURITY DEFINER SECURITY DEFINER は、関数を作成したユーザーの特権でこの関数を実行することを指定します。 これがデフォルト値です。 EXTERNAL キーワードは SQL 準拠に有効ですが、これはオプションです。
[ EXTERNAL ] SECURITY INVOKER SECURITY INVOKER 句は、関数を呼び出すユーザーの特権でこの関数を実行することを示します。 EXTERNAL キーワードは SQL 準拠に有効ですが、これはオプションです。
AUTHID DEFINER | AUTHID CURRENT_USER
  • AUTHID DEFINER 句は、[EXTERNAL] SECURITY DEFINER と同義です。 AUTHID 句を省略した場合、または AUTHID DEFINER を指定した場合は、関数所有者の権限を使用して、データベースオブジェクトへのアクセス権を決定します。
  • AUTHID CURRENT_USER 句は、[EXTERNAL] SECURITY INVOKER と同義です。 AUTHID CURRENT_USER が指定されている場合、関数を実行している現在のユーザーの権限を使用して、アクセス権を決定します。
PARALLEL { UNSAFE | RESTRICTED | SAFE } PARALLEL 句は、パラレルシーケンシャルスキャン (パラレルモード) の使用を有効にします。 パラレルシーケンシャルスキャンは、シリアルシーケンシャルスキャンとは対照的に、複数のワーカーを使用してクエリ中にパラレル関係をスキャンします。
  • このパラメーターが UNSAFE に設定されている場合、関数をパラレルモードで実行することはできません。 そのような関数が SQL ステートメントに存在する場合、シリアル実行プランが実施されます。 PARALLEL 句が省略されている場合、UNSAFE がデフォルトの設定です。
  • このパラメーターが RESTRICTED に設定されると、関数をパラレルモードで実行することができますが、実行はパラレルグループリーダーに制限されます。 特定の関係に関する資格にパラレル制限されたコンテンツがある場合、その関係がパラレル実行の際に選択されることはありません。
  • このパラメーターを SAFE に設定すると、この関数をパラレルモードで制限なしに実行できます。
COST execution_cost execution_cost は、関数の実行にかかる概算コストを示す正の値です。 単位は cpu_operator_cost です。 関数がセットを返す場合、返された各行のコストを示します。 値がより大きい場合、プランナーは必要以上に頻繁に関数を評価することを回避しようとします。
ROWS result_rows result_rows は正の値であり、プランナーが関数が返すと予想する行の推定数を示します。 この値は、関数がセットを返すことを宣言されている場合にのみ使用できます。 デフォルト値は 1,000 行です。
SET configuration_parameter { TO value | = value | FROM CURRENT } SET 句を使用すると、指定された構成パラメーターは関数の開始時に指定された値に設定され、関数の終了時に元の値に戻ります。 SET FROM CURRENT は、関数の開始時に適用される値として、パラメーターの現在の値を保存します。

関数に SET 句が指定されている場合、関数内で同じ変数に対して実行される SET LOCAL コマンドの影響はその関数に限定されます。 関数が終了すると、構成パラメーターは元の値に戻されます。 LOCAL を使用しない通常の SET コマンドは、SET 句をオーバーライドします。 これは、以前の SET LOCAL コマンドに似ています。 SET コマンドの効果は、現在のトランザクションがロールバックされない限り、関数が終了した後も持続します。

PRAGMA AUTONOMOUS_TRANSACTION PRAGMA AUTONOMOUS_TRANSACTION は、関数を自律型トランザクションとして設定するディレクティブです。
STRICT、LEAKPROOF、PARALLEL、COST、ROWS、および SET キーワードは、Oracle と互換性のある PolarDB データベースに拡張機能を提供します。 ただし、これらのキーワードは Oracle データベースではサポートされていません。

emp_comp 関数は 2 つの数値を入力としてアクセプトし、計算値を返します。 SELECT コマンドは、関数の使用方法を説明するために使用されます。

CREATE OR REPLACE FUNCTION emp_comp (
    p_sal NUMBER,
    p_comm NUMBER
) RETURN NUMBER
IS
BEGIN
    RETURN (p_sal + NVL(p_comm, 0)) * 24;
END;

SELECT ename "Name", sal "Salary", comm "Commission", emp_comp(sal, comm)
    "Total Compensation" FROM emp;

  Name | Salary | Commission | Total Compensation
--------+---------+------------+--------------------
 SMITH | 800.00 | | 19200.00
 ALLEN | 1600.00 | 300.00 | 45600.00
 WARD | 1250.00 | 500.00 | 42000.00
 JONES | 2975.00 | | 71400.00
 MARTIN | 1250.00 | 1400.00 | 63600.00
 BLAKE | 2850.00 | | 68400.00
 CLARK | 2450.00 | | 58800.00
 SCOTT | 3000.00 | | 72000.00
 KING | 5000.00 | | 120000.00
 TURNER | 1500.00 | 0.00 | 36000.00
 ADAMS | 1100.00 | | 26400.00
 JAMES | 950.00 | | 22800.00
 FORD | 3000.00 | | 72000.00
 MILLER | 1300.00 | | 31200.00
(14 行)

sal_range 関数は、給与が指定された範囲にある従業員の数を返します。 次の匿名ブロックは関数を複数回呼び出し、引数のデフォルト値が最初の 2 回の呼び出しで使用されます。

CREATE OR REPLACE FUNCTION sal_range (
    p_sal_min NUMBER DEFAULT 0,
    p_sal_max NUMBER DEFAULT 10000
) RETURN INTEGER
IS
    v_count INTEGER;
BEGIN
    SELECT COUNT(*) INTO v_count FROM emp
        WHERE sal BETWEEN p_sal_min AND p_sal_max;
    RETURN v_count;
END;

BEGIN
    DBMS_OUTPUT.PUT_LINE('Number of employees with a salary: ' ||
        sal_range);
    DBMS_OUTPUT.PUT_LINE('Number of employees with a salary of at least '
        || '$2000.00: ' || sal_range(2000.00));
    DBMS_OUTPUT.PUT_LINE('Number of employees with a salary between '
        || '$2000.00 and $3000.00: ' || sal_range(2000.00, 3000.00));

END;

Number of employees with a salary: 14
Number of employees with a salary of at least $ 2000.00: 6
Number of employees with a salary between $ 2000.00 and $ 3000.00: 5

次の例は、関数宣言で AUTHID CURRENT_USER 句と STRICT キーワードを使用する方法を示しています。

CREATE OR REPLACE FUNCTION dept_salaries(dept_id int) RETURN NUMBER
  STRICT
  AUTHID CURRENT_USER
BEGIN
  RETURN QUERY (SELECT sum(salary) FROM emp WHERE deptno = id);
END;

STRICT キーワードは、渡された入力パラメーターが NULL の場合にサーバーが NULL を返すよう指示するために含まれます。 NULL 値が渡された場合、関数は実行されません。

dept_salaries 関数は、関数を呼び出しているロールの特権で実行されます。 現在のユーザーが (従業員の給与を表示するために) emp テーブルをクエリする SELECT ステートメントを実行するための権限が十分でない場合、関数はエラーを報告します。 関数を定義したロールに関連付けられた権限を使用するようサーバーに指示するには、AUTHID CURRENT_USER 句を AUTHID DEFINER 句に置き換えます。