1.存储二进制数据
int sqlite3_bind_blob(sqlite3_stmt*,int,const void*,int n,void(*)(void*));
我们希望使用的是一套经过封装的COM接口,将上面这个函数封装为COM接口的形式
BindParaByIndex( LONG index,VARIANT val);
使用VARIANT变量来传递二进制数据,可以使用到它的一个SAFEARRAY指针,它保存了二进制数据的地址和二进制数据的字节长度。
在我们的COM接口中可以这样进行调用原始接口:
sqlite3_bind_blob(m_pStmt,val.parray,val.parray->rsground->cElement,sqlITE_TRANSIENT);
构造一个例子测试我们的接口:
BYTEData[] = {0x01,0x02,0x03,0x04,0x05};
CComSafeArray<byte> *pcsfa;
CComSafeArrayBoundbound[1];
bound[0].SetCount(5);
SetLowerBound(0);
pcsfa=newbyte>(bound,1);
for(LONGi= 0;i<(LONG)5;i++)
{
HRESULThr=pcsfa->SetAt(i,Data[i]);
}
_variant_tvariant;
variant.vt=VT_ARRAY|VT_UI1;
parray=m_psa;
将五个字节的数据封装到VARIANT变量中,然后调用相应的接口,将它们存储到数据库中,然后
调用下面的读取二进制接口,将数据读取出来,看是否读取的数据和存储的数据一致.
2.读取二进制数据
读取二进制参数需要用到下面两个sqlite提供的API:
const void *sqlite3_column_blob(sqlite3_stmt*,int iCol);
int sqlite3_column_bytes(sqlite3_stmt*,int iCol);
访问也通过COM接口来实现:
GetBlobData(LONG index,VARIANT* pval);
如何将原始接口读出来的数据封装到VARIANT结构中去呢,网上这方面的参考资料好少,差了不少资料,发现网上有不上SAFEARRAY的实现方案,但是我一一试了一下没有一个可以将二进制数读入SAFEARRAY结构的,Mentor给我推荐了一个CcomSafeArray类,这个类成功实现了数据的存储。
CComVariantcVal;
intnLen=sqlite3_column_bytes(m_pStmt,2)">nIndex);
constvoid*pcvData= (constvoid*)sqlite3_column_blob(nIndex);
BYTE*pData=newBYTE[nLen];
memcpy(pData,2)">pcvData,2)">nLen);
SetCount(LONG)nLen;pData[cVal=m_psa;
cVal.VT_UI1;
deletepData;
cVal.Detach(pVal);
OK,现在可以通过下面的代码来测试是否成功读取了所有的二进制数据。测试代码如下:
_variant_t val;
val = GetBlobData(nIndex); //nIndex表示BLOB类型数据的索引值
bytebuf[5];
if(val.vt== (VT_UI1|VT_ARRAY))
{
for(index= 0;index< 5;index++)
{
::SafeArrayGetElement(parray,&index,2)">buf+index);
}
}
for(intj= 0;j< 5;j++)
{
cout<<“0x”<<hex<<(int)buf[j]<<endl;//测试结果为0x01,0x05
}