Operating Systems
E.13 パフォーマンスとチューニング
else
len = sizeof(resultdata)/sizeof(TCHAR)-dtsize;
// Step 3: GetData
rc = SQLGetData(stmtHnd, 1,
SQL_C_TCHAR,
(SQLPOINTER)bufp, len*sizeof(TCHAR), &retchklen);
}
if (!_tcscmp(resultdata, clobdata)) { _tprintf(_T("Succeeded!!/n/n"));
} else {
_tprintf(_T("Failed!!/n/n"));
}
の特性上、アプリケーションが列をバインドするかSQLGetData操作を実行するかに関係な く、Oracle ODBC Driverでは列全体をフェッチする必要があるためです。
データソースを更新しないトランザクションを実行する場合
は、ODBCのSQLSetConnectAttr関数のSQL_ATTR_ACCESS_MODE属性 をSQL_MODE_READ_ONLYに設定します。
ODBCのエスケープ句を使用しない場合は、そのODBCのSQLSetConnectAttr関数また はSQLSetStmtAttr関数のSQL_ATTR_NOSCAN属性をtrueに設定します。
行数の多い表からデータを取得する場合は、ODBCのSQLFetch関数のかわり にODBCのSQLFetchScroll関数を使用します。
E.13.2 データソース構成オプション
この項では、次のODBCデータソース構成オプションを使用した場合のパフォーマンスへの影響を 説明します。
結果セットの有効化
このオプションによって、プロシージャ・コールから結果セット(RefCursorなど)を返すサ ポートが有効になります。デフォルトでは、結果セットを返すサポートが有効です。
Oracle ODBC Driverでは、RefCursorパラメータが存在するかどうかを判断するために、デ ータベース・サーバーを問い合せてプロシージャのパラメータ・セットとそのデータ型を判 別する必要があります。この問合せによって、最初にプロシージャが準備完了になり実行さ れると、追加のネットワーク・ラウンド・トリップが発生します。
LOBの有効化
このオプションによって、LOBを挿入および更新するサポートが有効になります。デフォル トは有効です。
Oracle ODBC Driverでは、LOBパラメータがあるかどうかを判断するために、データベー
ス・サーバーを問い合せて、INSERT文またはUPDATE文の各パラメータのデータ型を判別す る必要があります。この問合せによって、最初にINSERTまたはUPDATEが準備完了になり実 行されると、追加のネットワーク・ラウンドトリップが発生します。
関連項目:
LOBの詳細は、『Oracle Database SecureFilesおよびラージ・オブジェクト開発者ガイド』を 参照してください。
注意: LOBデータ圧縮を行うと、SecureFilesを圧縮して、ディスク、入出力およ
びREDOログを節約できます。この場合、圧縮により領域の使用効率が上がるた め、コストが低減されます。また、圧縮により入出力およびREDOログが縮小する ため、SecureFilesのパフォーマンスが向上します。
LOBデータを暗号化すると、データベースのセキュリティが強化されます。ランダ ムな読取りおよび書込みに対して暗号化データが使用可能になっている間、データ のセキュリティは向上します。
データを圧縮および暗号化する場合、追加のメモリーが消費されます。
TIMESTAMPをDATEとしてバインド
SQL_TIMESTAMPパラメータを適切なOracle Databaseデータ型としてバインドします。この オプションをTRUEに設定すると、SQL_TIMESTAMPはOracleのDATEデータ型としてバインド されます。このオプションをFALSEに設定する
と、SQL_TIMESTAMPはOracleのTIMESTAMPデータ型としてバインドされます。これがデフ ォルトです。
カーソル・クローズの有効化
ODBC関数SQLFreeStmtのSQL_CLOSEオプションは、関連するカーソルを文とともにクロ
ーズし、保留中のすべての結果を廃棄します。アプリケーションでは文を再度実行すること によってカーソルを再オープンでき、SQLPrepareを再度実行する必要はありません。このオ プションを使用する典型的な例は、しばらくの間アイドル状態になり、後で同じSQL文を再 利用するアプリケーションの場合です。この場合、アプリケーションがアイドル状態になっ ている間、関連するサーバー・リソースを解放できます。
Oracle ODBC Driverが位置するOCIでは、カーソルをクローズする機能をサポートしていませ
ん。したがって、デフォルトでは、SQL_CLOSEオプションはOracle ODBC Driverに影響を与 えません。カーソルおよび関連するリソースはデータベース上でオープンしたままです。
このオプションを有効にすると、データベース・サーバー上の関連するカーソルがクローズ します。ただし、その結果、SQL文の解析コンテキストが失われます。ODBCアプリケーシ ョンは文を再度実行でき、SQLPrepareをコールする必要はありません。ただし、内部的に
は、Oracle ODBC Driverは文全体を準備して実行する必要があります。このオプションを有
効にすると、文を1回準備して繰り返し実行するアプリケーションのパフォーマンスに大き な影響を与えます。
このオプションは、サーバー上のリソースを解放する必要がある場合のみ有効にしてくださ い。
フェッチ・バッファ・サイズ
odbc.iniファイルのフェッチ・バッファ・サイズ(FetchBufferSize)を、バイト単位で 指定した値に設定します。この値は、Oracle ODBC DriverがOracle Databaseからクライントの キャッシュに1回にプリフェッチするデータの行数を決定するのに必要なメモリー量で、ア プリケーション・プログラムが1回の問合せで要求する行数とは関係ありません。これによ って、パフォーマンスが向上します。
また、1回にフェッチするデータが20行未満であることが多いアプリケーションで、特に、
速度の遅いネットワーク接続である場合や負荷の大きいサーバーからフェッチする場合は、
アプリケーションの応答時間が改善されます。この設定値が高すぎると、応答時間に悪影響 が生じたり、大量のメモリーが消費される可能性があります。デフォルトは64,000バイトで す。アプリケーションに対して最適な値を選択してください。
LONGおよびLOBデータ型がある場合、Oracle ODBC Driverがプリフェッチする行数はこのフ ェッチ・バッファ・サイズで決まりません。LONGおよびLOBデータ型が含まれると、パフォ ーマンスの向上は最小限になり、過剰にメモリーが使用される可能性があります。Oracle
ODBC Driverはこのフェッチ・バッファ・サイズを無視し、LONGおよびLOBデータ型が存在
する場合は一定の行数のみプリフェッチします。
関連項目:
「SQLDriverConnect関数の接続文字列の書式」
E.13.3 DATEおよびTIMESTAMPデータ型
WHERE句でデータベースのDATE列が使用され、その列に索引がある場合は、パフォーマンスに影 響を与える可能性があります。次に例を示します。
SELECT * FROM EMP WHERE HIREDATE = ?
この例では、HIREDATE列の索引を使用して、問合せを迅速に実行できます。ただ
し、HIREDATEがDATE値で、Oracle ODBC Driverはこのパラメータ値をTIMESTAMPとして提供し ているため、Oracle Databaseの問合せオプティマイザは変換関数を適用する必要があります。誤っ た結果(パラメータ値に0以外の小数秒がある場合に発生する可能性があります)を防ぐために、オ プティマイザは、HIREDATE列に変換を適用するため、次のような文になります。
SELECT * FROM EMP WHERE TO_TIMESTAMP(HIREDATE) = ?
ただし、この場合はHIREDATE列で索引を使用できなくなります。かわりに、サーバーでは表の順 次スキャンを実行します。したがって、表に多数の行がある場合は時間がかかる可能性がありま す。このような場合の次善策として、Oracle ODBC DriverにはTIMESTAMPをDATEとしてバインド する接続オプションが用意されています。このオプションを有効にすると、Oracle ODBC
Driverは、SQL_TIMESTAMPパラメータをOracleのTIMESTAMPデータ型ではなくOracleのDATEデー タ型としてバインドします。これによって、問合せオプティマイザはDATE列で索引を使用できま す。
注意: このオプションは、DATE列をTIMESTAMP列としてバインドするMicrosoft Accessや
類似のプログラムで使用することを目的にしています。実際のTIMESTAMP列がある場 合、またはデータが失われる可能性がある場合は使用しないでください。Microsoft
Accessでは、主キーとして選択されたすべての列を使用してこの問合せを実行します。