bcp_init
一括コピー操作を初期化します。
構文
RETCODE bcp_init (
HDBC hdbc,
LPCTSTR szTable,
LPCTSTR szDataFile,
LPCTSTR szErrorFile,
INT eDirection);
引数
- hdbc
一括コピーが有効な ODBC 接続ハンドルです。
szTable
コピー操作の対象になるデータベース テーブルの名前です。この名前には、データベース名または所有者名を含めることもできます。たとえば、pubs.gracie.titles、pubs..titles、gracie.titles、および titles はすべて有効なテーブル名です。eDirection を DB_OUT に設定している場合は、szTable をデータベース ビューの名前にすることもできます。
eDirection を DB_OUT に設定し、bcp_exec を呼び出す前に bcp_control を使用して SELECT ステートメントを指定する場合は、bcp_init の szTable を NULL に設定する必要があります。
- szDataFile
コピー操作の対象になるユーザー ファイルの名前です。bcp_sendrow を使用して変数から直接データをコピーしている場合は、szDataFile を NULL に設定します。
- szErrorFile
進行状況メッセージ、エラー メッセージ、および何らかの理由でユーザー ファイルからテーブルにコピーできなかった任意の行のコピーを書き込むエラー ファイルの名前です。szErrorFile に NULL が渡されると、エラー ファイルは使用されません。
- eDirection
コピーの方向です。この値は DB_IN または DB_OUT のいずれかになります。DB_IN は、プログラム変数またはユーザー ファイルからテーブルへのコピーを示します。DB_OUT は、データベース テーブルからユーザー ファイルへのコピーを示します。DB_OUT を指定する場合は、ユーザー ファイル名を指定する必要があります。
戻り値
SUCCEED または FAIL を返します。
解説
bcp_init は、他の一括コピー関数を呼び出す前に呼び出します。bcp_init は、ワークステーションと SQL Server 間のデータの一括コピーに必要な初期化を実行します。
bcp_init 関数には、一括コピー関数で使用できる ODBC 接続ハンドルを指定する必要があります。このハンドルを有効にするには、割り当て済みの、接続されていない接続ハンドルで、SQL_COPT_SS_BCP を SQL_BCP_ON に設定して、SQLSetConnectAttr を使用します。接続済みのハンドルの属性を割り当てようとすると、エラーが発生します。
データ ファイルを指定すると、そのデータ ファイルではなく、データベースのコピー元またはコピー先のテーブルの構造が bcp_init で調査されます。bcp_init では、データベース テーブル、ビュー、または SELECT 結果セットの各列に基づいて、データ ファイルのデータ形式値を指定します。このデータ形式値には、各列のデータ型、長さのインジケータや NULL インジケータとターミネータ バイトの文字列がデータ内に存在するかどうか、および固定長データ型の幅も含まれます。bcp_init では、これらの値を次のように設定します。
- 指定するデータ型は、データベース テーブル、ビュー、または SELECT 結果セット内の列のデータ型です。データ型は、sqlncli.h に指定されている SQL Server ネイティブ データ型で列挙されます。データ自体は、そのデータのコンピュータ形式で表されます。つまり、integer データ型の列のデータは、データ ファイルを作成したコンピュータに基づいて、ビッグ エンディアンまたはリトル エンディアンの 4 バイト シーケンスで表されます。
- データベースのデータ型が固定長の場合は、データ ファイルのデータも固定長になります。データを処理する一括コピー関数 (bcp_exec など) では、データ行が解析されます。データ ファイル内のデータの長さは、データベース テーブル、ビュー、または SELECT 列リスト内で指定されるデータの長さと同じでなければなりません。たとえば、char(13) で定義されているデータベース列のデータは、ファイル内の各データ行では 13 文字で表す必要があります。データベース列で NULL 値を許容する場合は、固定長データにプレフィックスとして NULL インジケータを付けることができます。
- ターミネータ バイト シーケンスを定義すると、ターミネータ バイト シーケンスの長さが 0 に設定されます。
- データを SQL Server にコピーするときは、データ ファイルにデータベース テーブル内の各列に格納するデータが含まれている必要があります。データを SQL Server からコピーするときは、データベース テーブル、ビュー、または SELECT 結果セット内のすべての列のデータがデータ ファイルにコピーされます。
- データを SQL Server にコピーするときは、データ ファイル内の列の序数位置がデータベース テーブル内の列の序数位置と同じであることが必要です。データを SQL Server からコピーするときは、bcp_exec によりデータベース テーブル内の列の序数位置に基づいてデータが配置されます。
- データベースのデータ型が可変長 (varbinary(22) など) の場合、またはデータベース列に NULL 値を含めることができる場合は、データ ファイル内のデータにプレフィックスとして長さのインジケータや NULL インジケータを付けることができます。インジケータの幅は、データ型と一括コピーのバージョンによって異なります。bcp_control のオプションである BCP6xFILEFMT では、データ内のインジケータの幅が必要な幅より狭くなる時点を示すことで、以前の一括コピー データ ファイルとそれ以降のバージョンの SQL Server を実行しているサーバー間で互換性が維持されます。
データ ファイルに指定されているデータ形式の値を変更するには、bcp_columns と bcp_colfmt を呼び出します。
インデックスを含まないテーブルの場合は、データベース復旧モデルを SIMPLE または BULK_LOGGED に設定することで、SQL Server への一括コピーを最適化できます。詳細については、「一括インポートのパフォーマンスの最適化」および「ALTER DATABASE」を参照してください。
データ ファイルを使用しない場合は、列ごとにデータの形式とメモリ内の場所を指定して bcp_bind を呼び出してから、bcp_sendrow を使用して SQL Server にデータ行をコピーする必要があります。
例
select into/bulkcopy オプションを設定することで、インデックスを含まないテーブルで一括コピーを高速にすることができます。
// Variables like henv not specified.
HDBC hdbc;
SQLHSTMT hstmt;
// Application initiation, get an ODBC environment handle, allocate the
// hdbc, and so on.
...
// Enable bulk copy prior to connecting on allocated hdbc.
SQLSetConnectAttr(hdbc, SQL_COPT_SS_BCP, (SQLPOINTER) SQL_BCP_ON,
SQL_IS_INTEGER);
// Connect to the data source, return on error.
if (!SQL_SUCCEEDED(SQLConnect(hdbc, _T("myDSN"), SQL_NTS,
_T("myUser"), SQL_NTS, _T("myPwd"), SQL_NTS)))
{
// Raise error and return.
return;
}
// Get a statement handle and set the select into/bulkcopy database
// option to TRUE.
SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &hstmt);
if (!SQL_SUCCEEDED(SQLExecDirect(hstmt,
_T("ALTER DATABASE mydb SET RECOVERY SIMPLE"),
SQL_NTS)))
{
// Raise error and return.
return;
}
// Flush the statement handle.
while (SQL_SUCCEEDED(SQLMoreResults(hstmt)))
;
// Initialize bulk copy, perform copies, and so on.
...
// Turn off the select into/bulkcopy database option.
if (!SQL_SUCCEEDED(SQLExecDirect(hstmt,
_T("ALTER DATABASE mydb SET RECOVERY FULL"),
SQL_NTS)))
{
// Raise error and return.
return;
}
// Carry on.