EXECUTE ステートメント
EXECUTE ステートメントは、準備済み SQL ステートメントを実行します。
呼び出し
このステートメントは、アプリケーション・プログラムに組み込む方法のみ可能です。 これは、動的に作成できない実行可能ステートメントです。
許可
- モジュールで定義されていないグローバル変数に対する READ 特権
- モジュールで定義されているグローバル変数のモジュールに対する EXECUTE 特権
- モジュールで定義されているグローバル変数のモジュールが含まれているスキーマに対する EXECUTEIN 特権
- モジュールで定義されているグローバル変数のモジュールが含まれているスキーマに対するスキーマ DATAACCESS 権限
- モジュールで定義されていないグローバル変数に対する WRITE 特権
- モジュールで定義されているグローバル変数のモジュールに対する EXECUTE 特権
- モジュールで定義されているグローバル変数のモジュールが含まれているスキーマに対する EXECUTEIN 特権
- モジュールで定義されているグローバル変数のモジュールが含まれているスキーマに対するスキーマ DATAACCESS 権限
ステートメントの実行時に許可検査が行われるステートメント (DDL、GRANT、 および REVOKE ステートメント) の場合、このステートメントの許可 ID の特権には、 PREPARE ステートメントで指定されている SQL ステートメントを実行するための特権が含まれていなければなりません。 ステートメントの許可 ID は、DYNAMICRULES BIND オプションの影響を受けることがあります。
許可検査がステートメントの準備の時点で行われるステートメント (DML) の場合、PREPARE ステートメントによって指定された SQL ステートメントでは、それ以外の許可検査は行われません。
構文
説明
- statement-name
- 実行する準備済みのステートメントを指定します。 statement-name (ステートメント名) は既に準備済みのステートメントを指定していなければならず、 またそのステートメントが SELECT ステートメントであってはなりません。
- INTO
- この後に、
準備済みステートメントの出力パラメーター・マーカーから値を受け取るために使用される、ターゲットのリストを指定します。
ターゲットへの個々の割り当ては、リストに指定された順序で行われます。
割り当てでエラーが発生すると、値はターゲットに割り当てられず、
値はそれ以上ターゲットに割り当てられません。それまでに既にターゲットに割り当てられていた値はそのままになります。
動的 CALL ステートメントの場合は、プロシージャーに対する OUT および INOUT 引数に使用されるパラメーター・マーカーは、出力パラメーター・マーカーです。 ステートメントに出力パラメーター・マーカーを使用する場合は、 INTO 節を指定する必要があります (SQLSTATE 07007)。
- assignment-target
- 出力値の割り当てのための 1 つ以上のターゲットを示します。
結果行の最初の値はリスト中の最初のターゲット、その次の値は 2 番目のターゲット、以下同様に割り当てられます。
assignment-target のデータ・タイプが行タイプの場合は、assignment-target を 1 つだけ指定し (SQLSTATE 428HR)、列の数が行タイプ内のフィールドの数に一致し、またフェッチされる行の列のデータ・タイプが行タイプの対応するフィールドに割り当て可能である必要があります (SQLSTATE 42821)。
assignment-target のデータ・タイプが配列エレメントの場合は、assignment-target を正確に 1 つだけ指定する必要があります。
- global-variable-name
- 割り当てのターゲットとなるグローバル変数を指定します。
- host-variable-name
- 割り当てのターゲットとなるホスト変数を指定します。 LOB 出力値の場合、ターゲットとして可能なのは正規のホスト変数 (十分な大きさの場合)、LOB ロケーター変数、または LOB ファイル参照変数です。
- SQL-parameter-name
- 割り当てのターゲットとなるルーチン・パラメーターを識別します。
- SQL-variable-name
- 割り当てターゲットである SQL 変数を識別します。 SQL 変数は、使用する前に宣言しておかなければなりません。
- transition-variable-name
- 遷移行で更新する列を識別します。 transition-variable-name は、新しい値を識別する相関名によってオプションで修飾されている、トリガーのサブジェクト表にある列を識別していなければなりません。
- array-variable-name
- 配列タイプの SQL 変数、SQL パラメーター、またはグローバル変数を指定します。
- array-index
- 配列のどのエレメントが割り当てのターゲットとなるかを指定する式。通常配列の場合、array-index 式は INTEGER に割り当て可能でなければならず (SQLSTATE 428H1)、NULL 値にすることはできません。その値は、1 と、配列に定義された最大カーディナリティーとの間でなければなりません (SQLSTATE 2202E)。連想配列の場合、array-index 式は連想配列の指標データ・タイプに割り当て可能でなければならず (SQLSTATE 428H1)、NULL 値にすることはできません。
- field-reference
- 割り当てのターゲットとなる行タイプ値内のフィールドを指定します。 field-reference は、修飾子がこのフィールドが定義されている行の値を識別する場合、修飾の field-name として指定する必要があります。
- DESCRIPTOR result-descriptor-name
- 出力 SQLDA を指定します。
その内容は、ホスト変数についての有効な記述でなければなりません。
EXECUTE ステートメントが処理される前に、 ユーザーは、入力 SQLDA の以下のフィールドを設定する必要があります。
- SQLDA に用意する SQLVAR のエレメント数を示す SQLN
- SQLDA に割り振るストレージのバイト数を示す SQLDABC
- ステートメントの処理時にその SQLDA の使用される変数の数を示す SQLD
- 変数の属性を示す SQLVAR のオカレンス
SQLDA には、すべての SQLVAR オカレンスが入るだけの十分なストレージがなければなりません。 したがって、SQLDABC の値は 16 + SQLN*(N) 以上でなければなりません (N は 1 つの SQLVAR オカレンスの長さ)。
LOB または構造化データ・タイプの出力データを入れる必要がある場合には、 各出力パラメーター・マーカーごとに 2 つの SQLVAR 項目が必要になります。
SQLD に設定する値は、ゼロ以上で SQLN 以下でなければなりません。
- USING
- この後に、
準備済みステートメントの入力パラメーター・マーカーに置き換わる値を含む変数または式のリストを指定します。
動的 CALL ステートメントの場合、プロシージャーに対する IN および INOUT 引数に使用されるパラメーター・マーカーは、入力パラメーター・マーカーです。 その他のすべての動的ステートメントの場合、すべてのパラメーター・マーカーは入力パラメーター・マーカーです。 ステートメントに入力パラメーター・マーカーを使用する場合は、 USING 節を指定する必要があります (SQLSTATE 07004)。
- input-host-variable, ...
- ホスト変数の宣言規則に従って、 該当プログラムで宣言されているホスト変数を指定します。 変数の数は、準備されるステートメントの入力パラメーター・マーカーの数と同じでなければなりません。 n 番目の変数は、 準備済みステートメントの n 番目のパラメーター・マーカーに対応します。 場合によっては、ロケーター変数とファイル参照変数も、 パラメーター・マーカーの値のソースとして指定できます。
- expression
- 準備済みステートメントの対応する入力パラメーター・マーカーの入力として使用する式を指定します。host-variable 以外の式を指定できるのは、コンパウンド SQL (コンパイル済み) ステートメント内で EXECUTE ステートメントが発行される場合だけです。
- DESCRIPTOR input-descriptor-name
- 入力 SQLDA を指定します。
その内容は、ホスト変数についての有効な記述でなければなりません。EXECUTE ステートメントが処理される前に、 ユーザーは、入力 SQLDA の以下のフィールドを設定する必要があります。
- SQLDA に用意する SQLVAR のエレメント数を示す SQLN
- SQLDA に割り振るストレージのバイト数を示す SQLDABC
- ステートメントの処理時にその SQLDA の使用される変数の数を示す SQLD
- 変数の属性を示す SQLVAR のオカレンス
SQLDA には、すべての SQLVAR オカレンスが入るだけの十分なストレージがなければなりません。 したがって、SQLDABC の値は 16 + SQLN*(N) 以上でなければなりません (N は 1 つの SQLVAR オカレンスの長さ)。
LOB または構造化データ・タイプの入力データを入れる必要がある場合には、 各パラメーター・マーカーごとに 2 つの SQLVAR 項目が必要になります。
SQLD に設定する値は、ゼロ以上で SQLN 以下でなければなりません。
- FOR host-variable または integer-constant ROWS
-
ソース・データの行数を指定します。挿入操作またはマージ操作用の値は、USING 節で指定します。
host-variable または integer-constant が整数値 k に割り当てられます。 host-variable を指定する場合は integer または short 型にする必要があり、標識変数を含めることはできません。 k は 2 から 32767 の範囲でなければなりません。 FOR host-variable も integer-constant ROWS も指定しない場合、SQL はサイズ 1 の配列を使用して実行されます。
注
- 準備済みステートメントを実行する前に、
各入力パラメーター・マーカーはそれに対応する変数または式の値によって置き換えられます。
型付きパラメーター・マーカーの場合、ターゲット変数または式の属性は CAST 指定によって指定されます。
タイプなしパラメーター・マーカーの場合、
ターゲット変数または式の属性はパラメーター・マーカーのコンテキストに従って決定されます。
V は、パラメーター・マーカー P に対応する入力変数または式を表します。 V の値は、列への値の割り振り規則に従って、P のターゲット変数に割り当てられます。 したがって、
- V はターゲットと互換でなければなりません。
- V がストリングの場合、その長さはターゲットの長さ属性を超えることはできません。
- V が数値の場合、 V の整数部分の絶対値はターゲットの整数部分の絶対値の最大を超えることはできません。
- V の属性がターゲットの属性と同一でない場合、 その値はターゲットの属性に合うように変換されます。
準備済みステートメントを実行すると、P の代わりに使用される値は P のターゲット変数または P のターゲット式の結果になります。 例えば、V が CHAR(6) でターゲットが CHAR(8) の場合、 P の代わりに使用される値は V の値にブランクを 2 個付加したものになります。
- 動的 CALL ステートメントの場合は、準備済みステートメントの実行後は、
OUT および INOUT の各引数の戻り値は、
引数に使用された出力パラメーター・マーカーに対応する割り当てのターゲットに割り当てられます。
型付きパラメーター・マーカーの場合、ターゲット変数の属性は CAST 指定によって指定されます。
タイプなしパラメーター・マーカーの場合、ターゲット変数の属性は、プロシージャーのパラメーターの定義によって指定されます。
V は、パラメーター・マーカー P に対応する出力割り当てターゲットを表し、プロシージャーの引数 A に使用されます。 A の値は、列から値を検索するための規則に従って V に割り当てられます。 したがって、
- V は A と互換でなければなりません。
- V がストリングの場合、その長さは A の長さより短いものであってはなりません。 そうでないと A の値は切り捨てられます。
- V が数値の場合、 V の整数部分の最大絶対値は A の整数部分の絶対値より小さいものであってはなりません。
- V の属性が A の属性と同一でない場合、A の値は V の属性に合うように変換されます。
- 動的 SQL ステートメント・キャッシング: 動的および静的 SQL ステートメントの実行に必要な情報は、静的 SQL ステートメントが最初に参照された時点、または動的 SQL ステートメントが最初に準備された時点で、データベース・パッケージ・キャッシュに入れられます。
この情報は、無効になるか、キャッシュ・スペースが他のステートメントで必要になるか、
またはデータベースがシャットダウンされるまでは、パッケージ・キャッシュに存続します。
SQL ステートメントが実行または準備される場合に、 要求を出したアプリケーションに関連するパッケージ情報が、 システム・カタログからパッケージ・キャッシュにロードされます。 個々の SQL ステートメントの実際の実行可能セクションもキャッシュに入れられます。 静的 SQL セクションは、該当のステートメントが最初に参照された時点で、 システム・カタログから読み取られてパッケージ・キャッシュに入れられ、 動的 SQL セクションは作成後にキャッシュに直接入れられます。 動的 SQL セクションは、 PREPARE や EXECUTE IMMEDIATE などの明示的なステートメントによって作成されます。 一度作成された動的 SQL ステートメントのセクションが、 スペース管理のために削除された場合や、環境の変化によって無効になった場合に、 システムによるステートメントの暗黙的な準備によって、再作成されることがあります。
各 SQL ステートメントは、データベース・レベルでキャッシュされ、アプリケーション間で共有できます。 静的 SQL ステートメントは、同じパッケージを使用してアプリケーション間で共有されます。 動的 SQL ステートメントは、同じコンパイル環境と、 厳密に同じステートメント・テキストを使用してアプリケーション間で共有されます。 アプリケーションによって発行される各 SQL ステートメントのテキストは、 アプリケーションにローカルにキャッシュされ、暗黙的な準備が必要な場合に使用されます。 アプリケーション・プログラム中の各 PREPARE ステートメントは、1 つのステートメントをキャッシュできます。 アプリケーション・プログラム中のすべての EXECUTE IMMEDIATE ステートメントは、 同じスペースを共有し、これらの EXECUTE IMMEDIATE ステートメントに対しては、 キャッシュされるステートメントは同時に 1 つしか存在しません。 それぞれ異なる SQL ステートメントに対して、 同じ PREPARE またはいずれかの EXECUTE IMMEDIATE ステートメントが何度も発行される場合は、 最後のステートメントだけがキャッシュに入れられ、再使用の対象になります。 キャッシュの使用を最適化するには、 アプリケーションの開始時に多くの異なる PREPARE ステートメントを一度に発行し、 その後必要に応じて EXECUTE または OPEN ステートメントを発行することです。
動的 SQL ステートメントがキャッシュに入れられると、パッケージに準備された SQL ステートメントが
KEEPDYNAMIC NOオプションでバインドされている場合を除き、ステートメントを再度準備する必要なく複数の作業単位にわたりステートメントを再使用できます。 環境が変更された場合に必要であれば、システムはこのステートメントを再コンパイルします。以下のイベントは、次の PREPARE、EXECUTE、EXECUTE IMMEDIATE、または OPEN の要求時に、 キャッシュされた動的ステートメントが暗黙的に準備される原因となる環境またはデータ・オブジェクトの変更の例です。- ALTER FUNCTION
- ALTER METHOD
- ALTER NICKNAME
- ALTER PROCEDURE
- ALTER SERVER
- ALTER TABLE
- ALTER TABLESPACE
- ALTER TYPE
- CREATE FUNCTION
- CREATE FUNCTION MAPPING
- CREATE INDEX
- CREATE METHOD
- CREATE PROCEDURE
- CREATE TABLE
- CREATE TEMPORARY TABLESPACE
- CREATE TRIGGER
- CREATE TYPE
- DROP (すべてのオブジェクト)
- 表または索引の RUNSTATS
- ビューが作動不能になる原因となるすべてのアクション
- システム・カタログ表の統計の UPDATE
- SET CURRENT DEGREE
- SET PATH
- SET QUERY OPTIMIZATION
- SET SCHEMA
- SET SERVER OPTION
キャッシュに入れられる動的 SQL ステートメントから予想される動作の概略は、以下のようになります。- PREPARE 要求: 以後同じステートメントの準備に、
セクションが有効であればステートメントのコンパイルのコストがかかりません。
現在キャッシュに入れられているセクションのコストとカーディナリティーの見積もりが戻されます。
それらの値は、
同じ SQL ステートメントに対するそれより前の PREPARE から戻される値とは違っている場合があります。
PREPARE ステートメントは、
KEEPDYNAMIC NOでバインドされたパッケージにそのステートメントが関連付けられている場合を除き、COMMIT ステートメントまたは ROLLBACK ステートメントを発行した後に発行する必要はありません。 - EXECUTE 要求: 元の PREPARE 以後にステートメントが無効になった場合に、 ステートメントを暗黙的に準備するコストが EXECUTE ステートメントにかかることがあります。 セクションが暗黙的に準備される場合、当初の PREPARE ステートメントの環境でなく、 現行の環境が使用されます。
- EXECUTE IMMEDIATE 要求: 以後同じステートメントに対して EXECUTE IMMEDIATE ステートメントを出す際に、 セクションが有効であればステートメントのコンパイルのコストがかかりません。
- OPEN 要求: 当初の PREPARE ステートメント以後にステートメントが無効になった場合、 ステートメントを暗黙的に準備するコストが動的に定義されたカーソルに対する OPEN 要求にかかることがあります。 セクションが暗黙的に準備される場合、当初の PREPARE ステートメントの環境でなく、 現行の環境が使用されます。
- FETCH 要求: 予想される動作の変化はありません。
- ROLLBACK:
ロールバック操作の影響を受ける作業単位で準備されたか暗黙的に準備された動的 SQL ステートメントだけが無効になります。
KEEPDYNAMIC NOを指定してバインドしたパッケージと関連付けられている非アクティブな動的 SQL ステートメントは、 ROLLBACK 操作の後にアプリケーションの SQL コンテキストから除去されるため、アプリケーションでそれらを実行する場合には、再度明示的に準備する必要があります。 動的 SQL ステートメントは、以前と同様データベース・レベルでキャッシュされるため、以後 PREPARE 要求を行うときにこのセクションがまだ有効であれば、ステートメントのコンパイルのコストがかかりません。 - COMMIT:
動的 SQL ステートメントは無効になりませんが、確立されたロックは解放されます。
WITH HOLDオプションで定義されていないカーソルはクローズされ、そのロックは解放されます。WITH HOLDオプションを指定して定義したオープン・カーソルは、そのパッケージとセクション・ロックを保持し、 コミット処理中およびその後にアクティブなセクションを保護します。KEEPDYNAMIC NOオプションを指定してバインドした動的 SQL ステートメントは、トランザクション境界の後に準備済み状態にならないため、アプリケーションでそれらを実行する場合には、再度明示的に準備する必要があります。WITH HOLDオプションを指定して定義したオープン・カーソル用に準備された SELECT ステートメントは、カーソルがクローズされるトランザクション境界に到達するまで準備済み状態になります。KEEPDYNAMIC NOを指定してバインドしたパッケージと関連付けられている非アクティブな動的 SQL ステートメントは、コミット操作の後にアプリケーションの SQL コンテキストから除去されるため、アプリケーションでそれらを実行する場合には、再度明示的に準備する必要があります。
暗黙の準備の過程でエラーが生じると、 その暗黙の準備の原因となった要求にエラーが戻されます (SQLSTATE 56098)。
例
h1 - h4 は、TDEPT の形式に対応します。
strcpy (s,"INSERT INTO TDEPT VALUES(?,?,?,?)");
EXEC SQL PREPARE DEPT_INSERT FROM :s;
.
.
(Check for successful execution and put values into :h1, :h2, :h3, :h4)
.
.
EXEC SQL EXECUTE DEPT_INSERT USING :h1, :h2,
:h3, :h4; EXECUTE S3 USING DESCRIPTOR :sqlda3 CREATE PROCEDURE GIVE_BONUS (IN EMPNO INTEGER,
IN DEPTNO INTEGER,
OUT CHEQUE INTEGER,
INOUT BONUS DEC(6,0))
... プロシージャーを C アプリケーションから動的に呼び出します。
プロシージャーは、以下のホスト変数を入力として取ります。
- employee。従業員の ID 番号。
- dept。部門番号。
- bonus。従業員の賞与。
- cheque_no。小切手の ID 番号。
- bonus。実際の賞与額 (調整後の)
strcpy (s, "CALL GIVE_BONUS(?, ?, ?, ?)");
EXEC SQL PREPARE DO_BONUS FROM :s;
.
.
/* Check for successful execution and put values into
:employee, :dept, and :bonus */
.
.
EXEC SQL EXECUTE DO_BONUS INTO :cheque_no, :bonus
USING :employee, :dept, :bonus;
.
.
/* Check for successful execution and process the
values returned in :cheque_no and :bonus */