新闻资讯
看你所看,想你所想

SAFEARRAY

SAFEARRAY

SAFEARRAY的主要目的是用于automation中的数组型参数的传递。

基本介绍

  • 外文名:SAFEARRAY
  • 用于:automation中的数组型参数的传递
  • 属于:一个自动化数据类型
  • 使用:通用调度器(oleaut32.dll)

步骤

SAFEARRAY的主要目的是用于automation中的数组型参数的传递。SafeArray是一个自动化数据类型,他使用了通用调度器(oleaut32.dll),如果採用自己定义的数组,那幺要发布自己的proxy / stub dll.实质上SafeArray就是将通常的数组增加一个描述符,说明其维数、长度、边界、元素类型等信息。SafeArray也并不单独使用,而是将其再包装到VARIANT类型的变数中,然后才作为参数传送出去。在VARIANT的vt成员的值如果包含VT_ARRAY|...,那幺它所封装的就是一个SafeArray,它的parray成员即是指向SafeArray的指针。 SafeArray中元素的类型可以是VARIANT能封装的任何类型,包括VARIANT类型本身。
vt的取值如下表:
vt值类型
VT_UI1无符号1位元组整数(BYTE)数组
VT_UI2无符号2位元组整数(WORD)数组
VT_UI4无符号4位元组整数(DWORD)数组
VT_UINT无符号整数(UINT)数组
VT_INT有符号整数(INT)数组
VT_I1有符号1位元组整数数组
VT_I2有符号2位元组整数数组
VT_I4有符号4位元组整数数组
VT_R4IEEE 4位元组浮点数(float)数组
VT_R8IEEE 8位元组浮点数(double)数组
VT_CY8位元组定点数货币值数组
VT_BSTRVB字元串数组
VT_DECIMAL12位元组定点数(大数字)数组
VT_ERROR标準错误编号数组
VT_BOOL布尔值数组
VT_DATE日期型数组
VT_VARIANTVB Variant类型数组
使用SafeArray的具体步骤:

方法一

包装一个SafeArray
(1). 定义变数,如:
VARIANT varChunk;
SAFEARRAY *psa;
SAFEARRAYBOUND rgsabound[1];
(2). 创建SafeArray描述符:
uIsRead=f.Read(bVal,ChunkSize);//read array from a file.
if(uIsRead==0)break;
rgsabound[0].cElements =uIsRead;
rgsabound[0].lLbound = 0;
psa = SafeArrayCreate(VT_UI1,1,rgsabound);
(3). 放置数据元素到SafeArray:
for(long index=0;index<uIsRead;index++)
{
if(FAILED(SafeArrayPutElement(psa,&index,&bVal)))
::MessageBox(NULL,"出毛病了。","提示",MB_OK | MB_ICONWARNING);
}
一个一个地放,挺麻烦的。
(4). 封装到VARIANT内:
varChunk.vt = VT_ARRAY|VT_UI1;
varChunk.parray = psa;
这样就可以将varChunk作为参数传送出去了。
读取SafeArray中的数据的步骤:
(1). 用SafeArrayGetElement一个一个地读
BYTE buf[lIsRead];
for(long index=0;index<lIsRead;index++)
{
::SafeArrayGetElement(varChunk.parray,&index,buf+index);
}
就读到缓冲区buf里了。

方法二

用SafeArrayAccessData直接读写SafeArray缓冲区:
(1). 读缓冲区:
BYTE *buf;
SafeArrayAccessData(varChunk.parray, (void **)&buf);
f.Write(buf,lIsRead);
SafeArrayUnaccessData(varChunk.parray);
(2). 写缓冲区:
BYTE *buf;
::SafeArrayAccessData(psa, (void **)&buf);
for(long index=0;index<uIsRead;index++)
{
buf=bVal;
}
::SafeArrayUnaccessData(psa);
varChunk.vt = VT_ARRAY|VT_UI1;
varChunk.parray = psa;
这种方法读写SafeArray都可以,它直接操纵SafeArray的数据缓冲区,比用SafeArrayGetElement和 SafeArrayPutElement速度快。特别适合于读取数据。但用完之后不要忘了调用::SafeArrayUnaccessData (psa),否则会出错的。
如果SafeArray中存的是BSTR的二维数组,则代码如下:
if(varChunk.vt = VT_ARRAY | VT_BSTR)
{
BSTR* buf;
long LBound; // 数组下界
long UBound; // 数组上界
SafeArrayAccessData(varChunk.parray, (void **)&buf);
SafeArrayGetLBound(varChunk.parray, 1, &LBound);
SafeArrayGetUBound(varChunk.parray, 1, &UBound);
for(long i = LBound; i < UBound; i ++)
{
CString str(buf);
MessageBox(str);
}
SafeArrayUnaccessData(varChunk.parray);
}

转载请注明出处海之美文 » SAFEARRAY

相关推荐

    声明:此文信息来源于网络,登载此文只为提供信息参考,并不用于任何商业目的。如有侵权,请及时联系我们:ailianmeng11@163.com