掲載元

Oracle Magazine
2005年11月/12月
開発者:ODP.NET

優れたLOBの提供
Mark A. Williams著

ODP.NETの新機能により、LOBの処理がこれまでよりも簡単になります。

.NETアプリケーションでOracleデータベースのデータにアクセスする方法はいろいろありますが、機能とパフォーマンスの点に関しては、Oracle Data Provider for .NET(ODP .NET)が、Oracleデータベースを使用する.NETアプリケーションに接続するための最良の選択肢となります。

このODP.NETのコラムでは、Oracle Database 10g Release 2でODP.NET 10g Release 10.2およびラージ・オブジェクト(LOB)データを使用する方法について説明します。

ODP.NET LOBのサポート

LOBデータには、バイナリと文字の2つの基本型があり、いずれもODP.NETからアクセスできます。LOBデータ型は、非常に柔軟性があり、非常に大量のデータの処理と同様に、少量のデータ処理にも適しています。 LOBの正確な最大サイズは、データベースの構成によって異なりますが、大体8~128テラバイトの範囲になります。 反対に、LOBデータは1バイトまたは1文字まで小さくすることもできます。ただし、少量の文字データを格納するには、VARCHAR2などの従来のデータ型を使用する方が適切です。 バイナリ・データは、表内のBLOB列として、またはデータベースの外にあるファイル・システムに常駐するBFILEとして格納されます。 文字データは、CLOB列のデータベース・キャラクタ・セットまたはNCLOB列の各国語キャラクタ・セットを使用して格納されます。

ODP.NETを使用すると、LOBデータへのアクセスおよびLOBデータでの作業が簡単になります。 ODP.NET内のすべてのLOBオブジェクトは、.NETフレームワークが提供する Stream クラスから継承される接続オブジェクトです。 LOBデータ型は、 OracleBlob クラス、 OracleBFile クラス、および OracleClob クラスを介して、ODP.NETでサポートされています。 OracleClob クラスは、CLOBとNCLOBの両方のデータ型を表します。 IsNCLOB プロパティは、CLOBオブジェクトに含まれているデータ型を区別します。

LOBとして格納されているデータは、 OracleDataReader クラスのインスタンスを介してデータベースから読み取られます。 OracleDataReader クラスを指定すると、LOBデータをオブジェクトまたはスカラー・データの配列として使用できます。 LOBデータをオブジェクトとして使用するには、 GetOracleBlob GetOracleBFile 、または GetOracleClob などのタイプ・アクセッサを起動します。 LOBデータを配列として使用する場合は、 GetBytes メソッド(バイナリ・データ用)または GetChars メソッド(文字データ用)を使用して、一度に特定のバイト数または文字数を読み取り、配列に移入します。 このコラムでは、外部のBFILEに格納されているデータではなく、データベースに格納されているLOBデータでの作業について説明します。

InitialLOBFetchSizeプロパティ。 InitialLOBFetchSize プロパティは、 OracleCommand オブジェクトに設定されています。 OracleDataReader オブジェクトは、このプロパティの値を関連する OracleCommand オブジェクトから継承します。 LOBオブジェクトでの読取り操作中にデータベースからフェッチされるLOBデータの量は、 InitialLOBFetchSize プロパティによって決まります。 文字データ(CLOBおよびNCLOB)を使用する場合、この値で読み込む文字数を指定します。 バイナリ・データ(BLOB)を使用する場合は、この値で読み込むバイト数を指定します。 このプロパティの動作および機能は、Oracle Database 10g Release 2で変更されています。

このリリース以前では、 InitialLOBFetchSize プロパティの適正な値は、0または1から32,767(32KB)の間の整数でした。 Oracle Database 10g Release 2以降では、このプロパティの適正な値は、-1、0、または1から2,147,483,647(2GB)の間の整数です。 比較すると、最大値が大幅に増えています。 このプロパティは、LOBからデータを取得する方法や、取得するデータ量の両方を制御します。 このプロパティに対して、さまざまな値を使用する際に使用できるメソッドの完全なリストについては、Oracle Data Provider for .NET開発者ガイドを参照してください。

InitialLOBFetchSizeが0の場合。 ODP.NETの以前のリリース同様、 InitialLOBFetchSize プロパティのデフォルト値は0です。0に設定されている場合、LOBオブジェクトのすべてのタイプ・アクセッサは有効で、クライアント アプリケーションで呼び出すことができます。 これにより高い柔軟性が得られます。 GetOracleBlob または GetOracleClob タイプ・アクセッサ・メソッドを起動することで、LOBをオブジェクトとして使用できます。また、 GetBytes または GetChars メソッドを起動して、LOBを配列として使用できます。

InitialLOBFetchSizeが0より大きい場合。 InitialLOBFetchSize プロパティが1から2,147,483,647(2GB)の間の整数に設定されている場合、 OracleDataReader オブジェクトで read メソッドが起動されると、ODP.NETはこの数のバイトまたは文字を読み取り、キャッシュします。 LOBの合計サイズがこの数値より少ない場合は、LOBデータ全体が読み取られます。 Oracle Database 10g Release 2ではパフォーマンスが強化されているため、タイプ・アクセッサ・メソッドが起動され、 InitialLOBFetchSize が0より大きい場合、LOBデータ全体が返されます。

InitialLOBFetchSize プロパティの最大値が増えたことに加え、タイプ・アクセッサ・メソッドの使用方法も変更されています。 GetOracleBlob および GetOracleClob タイプ・アクセッサは、 InitialLOBFetchSize パラメータが0より大きい時に起動できるようになりました。(Oracleデータベースの以前のリリースでは、 InitialLOBFetchSize が0より大きい場合、主キー、ROWID、または一意な列を選択リストに含める必要がありました。)

InitialLOBFetchSizeが-1の場合。 Oracle Database 10g Release 2以降では、 InitialLOBFetchSize プロパティの値に-1を設定できます。プロパティが-1に設定されている場合、列にあるすべてのLOBデータが読取り操作中に返されます。 この値を使用する場合、主キー、ROWID、または一意な列を文の選択リストに含める必要はありません。 ただし、この場合は、LOBをオブジェクトとして使用することはできません。これは、 GetOracleBlob および GetOracleClob タイプ・アクセッサは、 InitialLOBFetchSize が-1のときに使用できないためです。 GetBytes または GetChars メソッドなどの別のメソッドを使用して、LOBデータを取得する必要があります。

戦略

新しい機能が加わり、制約が少なくなったおかげで、Oracle Database 10g Release 2を使用して、より簡単かつ効果的にLOBデータとODP.NETで作業できるようになりました。開発者は、 InitialLOBFetchSize プロパティを設定する代わりに、 GetOracleBlob および GetOracleClob を使用して、柔軟性とパフォーマンスのいずれかを選択する必要はなくなりました。 これからは、 InitialLOBFetchSize プロパティを設定することで、向上したパフォーマンスを得て、LOBデータをオブジェクトとして使用する利点を享受できます。

新しいアプリケーションを開発するには、いくつかの選択をおこなう必要があります。 自分のアプリケーションにとって最良の選択をするには、自分のニーズに合う方法で利用可能な機能を使用しなければなりません。 ガイドラインには常に限界に関する条件と例外事項がありますが、 InitialLOBFetchSize プロパティを適切に設定し、Oracle Database 10g Release 2の新しいパフォーマンス機能と拡張機能を活用すると、アプリケーションの柔軟性が増し、パフォーマンスが向上します。

Oracle Data Provider for .NET Developer's Guide (US OTN、英語)ページにある文献を参照してください。

ダウンロード
このコラムのサンプル・アプリケーション
ODP.NET 10g
Oracle Developer Tools for Visual Studio .NET (US OTN、英語)



InitialLOBFetchSize プロパティの適正値を決定する際には、次の2つの点を考慮してください。

  • 設計時にLOBデータのサイズがわかっているか。
  • LOBデータのサイズは均一か、それとも大きく異なるか。


設計時にLOBデータのサイズがわからない場合は、 InitialLOBFetchSize プロパティはデフォルト値の0とします。LOBデータのサイズがわかっている場合は、2つ目の点を考えます。 LOBのサイズがほとんど均一の場合、つまり各LOBがほぼ同じサイズの場合は、 InitialLOBFetchSize プロパティの値には、データベース行の少なくとも80%を含めることができる値を設定します。 LOBデータが極めて均一な場合、つまり各LOBが完全に同じサイズの場合は、このプロパティの値にそのサイズを設定します。 反対に、LOBデータのサイズが大きく異なる場合は、 InitialLOBFetchSize プロパティの値はデフォルトの0にします。アプリケーションはそれぞれ異なるので、本当に決めることができるのは、データのサイズが均一なのか異なるのか、このプロパティに対する適切な設定は何かだけです。

コード・リスト1: BLOBとして格納されているイメージの取得と表示

private void btnDisplay_Click(object sender, System.EventArgs e)
{
  // create and open connection
  // change for your environment
  string connStr = "User Id="pm;" Password="pm;" Data Source="ora10gR2;" Pooling=false";
  OracleConnection con = new OracleConnection(connStr);
  con.Open();

  // statement to get a blob
  string sql = "select ad_composite from print_media where product_id="3106" and ad_id=13001";
  
  // create command object
  // InitialLOBFetchSize defaults to 0
  OracleCommand cmd = new OracleCommand(sql, con);

  // create a datareader
  OracleDataReader dr = cmd.ExecuteReader();

  // read the single row result
  dr.Read();

  // use typed accessor to retrieve the blob
  OracleBlob blob = dr.GetOracleBlob(0);

  // create a memory stream from the blob
  MemoryStream ms = new MemoryStream(blob.Value);
    
  // set the image property equal to a bitmap
  // created from the memory stream
  pictureBox1.Image = new Bitmap(ms);
}


実装

以前のリリースと同様、Oracle Database 10gRelease 2にはサンプル・スキーマのセットが同梱されています。 PM サンプル・スキーマには、LOBデータのアクセスのテストに使用できる print_media という表が含まれています。 リスト1のサンプル・コードは、 ad_composite というBLOB列に格納されているイメージを取得する基本的なメソッドを示しています。 このシンプルなWindowsアプリケーション・プロジェクトには、 btnDisplay というボタンと pictureBox1 という画像ボックスが含まれています。 ad_composite 列に格納されているデータのサイズがわからないため、 InitialLOBFetchSize プロパティの値はデフォルトの0にしました。リスト1のコードを実行した結果は図1に示されています。

図1
図1



Mark A. Williams mawilliams@cheshamdbs.com )氏は、Oracle ACE、Oracle Certified Professional DBAであり、『 Pro .NET Oracle Programming 』(Apress、2004年)の著者でもあります。 Williams氏は、Windows環境でのOracleのソリューションに焦点を当てており、Oracle Technology NetworkのOracle Data Provider for .NETフォーラムにも貢献しています。