OLE DB での Seek メソッドの使用
Seek メソッドは、Microsoft SQL Server Compact 3.5 (SQL Server Compact 3.5) のインデックスに対して、クライアントから使用される最も頻度の高いメソッドです。Seek を使用すると、カーソル上の行を非常に高速に検索できます。
シークの使用
Seek メソッドでは、検索キーの列に定義されているインデックスが正常に機能する必要があります。ほとんどの Seek 操作は特定の値を対象としていますが、"Greater than" や "Less than" など、他の比較演算子を使用して検索することもできます。
IRowsetIndex::Seek は、OLE DB でデータの取得と設定に使用されるアクセサ メカニズムを使用して、プロバイダに値を渡します。Seek メソッドに使用されるアクセサには、IRowset::GetData および IRowset::SetData のアクセサより多くの制限があります。アクセサは、各列をインデックス キーに表示される順番にバインドする必要があります。
IRowsetPosition インターフェイスはスクロール可能なカーソルでのみサポートされます。
例
次の例は、OLE DB Provider for SQL Server Compact 3.5 を使用して、インデックスに対して IRowsetIndex::Seek を使用する方法を示しています。この例には、関数のうち、Seek メソッドに関連する部分のみが含まれています。
次の例は、32 ビットと 64 ビットの両方のプラットフォーム用に更新されています。64 ビット互換型は sqlce_oledb.h ネイティブ ヘッダー ファイルに含まれています。sqlce_oledb.h ネイティブ ヘッダー ファイルは %ProgramFiles%\Microsoft SQL Server Compact Edition\v3.5\Include フォルダにあります。詳細については、Visual Studio 2008 SP1 のドキュメントの OLE DB 64 ビット情報のトピックを参照してください。
TableID.eKind = DBKIND_NAME;
TableID.uName.pwszName = (WCHAR*)TABLE_EMPLOYEE;
IndexID.eKind = DBKIND_NAME;
IndexID.uName.pwszName = L"PK_Employees";
// Request ability to use IRowsetChange interface.
rowsetpropset[0].cProperties = 1;
rowsetpropset[0].guidPropertySet = DBPROPSET_ROWSET;
rowsetpropset[0].rgProperties = rowsetprop;
rowsetprop[0].dwPropertyID = DBPROP_IRowsetIndex;
rowsetprop[0].dwOptions = DBPROPOPTIONS_REQUIRED;
rowsetprop[0].colid = DB_NULLID;
rowsetprop[0].vValue.vt = VT_BOOL;
rowsetprop[0].vValue.boolVal = VARIANT_TRUE;
// Open the table using the index.
hr = pIOpenRowset->OpenRowset(NULL, &TableID, &IndexID,
IID_IRowsetIndex, sizeof(rowsetpropset)/sizeof(rowsetpropset[0]),
rowsetpropset, (IUnknown**) &pIRowsetIndex);
if(FAILED(hr))
{
goto Exit;
}
// Get the IRowset interface.
hr = pIRowsetIndex->QueryInterface(IID_IRowset, (void**) &pIRowset);
if(FAILED(hr))
{
goto Exit;
}
///////////////////////////////////////////////////////////////////////
// Steps to get column data using IcolumnsInfo have been removed
///////////////////////////////////////////////////////////////////////
// Create a DBBINDING array.
dwBindingSize = sizeof(pwszEmployees)/sizeof(pwszEmployees[0]);
prgBinding = (DBBINDING*)CoTaskMemAlloc(sizeof(DBBINDING)*dwBindingSize);
if (NULL == prgBinding)
{
hr = E_OUTOFMEMORY;
goto Exit;
}
// Set initial offset for binding position.
dwOffset = 0;
// Prepare structures to create an accessor for each index.
for (dwIndex = 0; dwIndex < dwBindingSize; ++dwIndex)
{
if (!GetColumnOrdinal(pDBColumnInfo, ulNumCols, pwszEmployees[dwIndex], &dwOrdinal))
{
hr = E_FAIL;
goto Exit;
}
prgBinding[dwIndex].iOrdinal = dwOrdinal;
prgBinding[dwIndex].dwPart = DBPART_VALUE | DBPART_STATUS | DBPART_LENGTH;
prgBinding[dwIndex].obLength = dwOffset;
prgBinding[dwIndex].obStatus = prgBinding[dwIndex].obLength + sizeof(DBLENGTH);
prgBinding[dwIndex].obValue = prgBinding[dwIndex].obStatus + sizeof(DBSTATUS);
prgBinding[dwIndex].pTypeInfo = NULL;
prgBinding[dwIndex].pBindExt = NULL;
prgBinding[dwIndex].dwMemOwner = DBMEMOWNER_CLIENTOWNED;
prgBinding[dwIndex].dwFlags = 0;
prgBinding[dwIndex].bPrecision = pDBColumnInfo[dwOrdinal].bPrecision;
prgBinding[dwIndex].bScale = pDBColumnInfo[dwOrdinal].bScale;
///////////////////////////////////////////////////////////////////////
// Case-specific binding information has been removed.
///////////////////////////////////////////////////////////////////////
prgBinding[dwIndex].pObject NULL;
prgBinding[dwIndex].wType = pDBColumnInfo[dwOrdinal].wType;
if(DBTYPE_WSTR == pDBColumnInfo[dwOrdinal].wType)
{
prgBinding[dwIndex].cbMaxLen = pDBColumnInfo[dwOrdinal].ulColumnSize
* sizeof(WCHAR);
}
else
{
prgBinding[dwIndex].cbMaxLen = pDBColumnInfo[dwOrdinal].ulColumnSize;
}
// Calculate and align the offset.
}
// Get IAccessor interface.
hr = pIRowset->QueryInterface(IID_IAccessor, (void**)&pIAccessor);
if(FAILED(hr))
{
goto Exit;
}
// Create the accessor.
hr = pIAccessor->CreateAccessor(DBACCESSOR_ROWDATA, dwBindingSize,
prgBinding, 0, &hAccessor, NULL);
if(FAILED(hr))
{
goto Exit;
}
// Allocate data buffer for seek and retrieve operation.
pData = (BYTE*)CoTaskMemAlloc(dwOffset);
if (NULL == pData)
{
hr = E_OUTOFMEMORY;
goto Exit;
}
// Set data buffer to zero.
//
memset(pData, 0, dwOffset);
// Set data buffer for seek operation by specifying the
// dwEmployeeID variable that is passed to the function.
*(DBLENGTH*)(pData+prgBinding[0].obLength) = 4;
*(DBSTATUS*)(pData+prgBinding[0].obStatus) = DBSTATUS_S_OK;
*(int*)(pData+prgBinding[0].obValue) = dwEmployeeID;
// Seek for the first row where the value of the selected column
// is dwEmployeeID.
hr = pIRowsetIndex->Seek(hAccessor, 1, pData, DBSEEK_FIRSTEQ);
if(FAILED(hr))
{
goto Exit;
}
// Retrieve a row handle for the row resulting from the seek.
hr = pIRowset->GetNextRows(DB_NULL_HCHAPTER, 0, 1, &cRowsObtained,
&prghRows);
if(FAILED(hr))
{
goto Exit;
}
///////////////////////////////////////////////////////////////////////
// Perform programming logic here on the
// returned rowset, and then release the rowset.
///////////////////////////////////////////////////////////////////////
Exit:
///////////////////////////////////////////////////////////////////////
// This is where the resources are released.
///////////////////////////////////////////////////////////////////////
return hr;
参照
概念
OLE DB インデックス (SQL Server Compact)