VARIANTとVARIANTARG
COMでは、Visual Basic互換の弁別子を持つ共用体VARIANT、VARIANTARGを多用します。
弁別子とは、構造体内にある名前なし共用体の区別をする整数です。
VARIANTの弁別子は、short VARIANT::vtです。
VARIANTARGは、VARIANTの別名です。VARIANTは、tagVARIANTのtypedefで、VARAINTARGも同様にtagVARIANTのtypedefです。
VARIANT構造体は、以下の構成となっています。
typedef struct tagVARIANT {
VARTYPE vt;
unsigned short wReserved1;
unsigned short wReserved2;
unsigned short wReserved3;
union {
unsigned char bVal; // vtはVT_UI1
short iVal; // vtはVT_I2
long lVal; // vtはVT_I4
float fltVal; // vtはVT_R4
double dblVal; // vtはVT_R8
VARIANT_BOOL boolVal; // vtはVT_BOOL
SCODE scode; // vtはVT_ERROR
CY cyVal; // vtはVT_CY
DATE date; // vtはVT_DATE
BSTR bstrVal; // vtはVT_BSTR
IUnknown* punkVal; // vtはVT_UNKNOWN
IDispatch* pdispVal; // vtはVT_DISPATCH
SAFEARRAY* parray; // vtはVT_ARRAY|*
unsigned char* pbVal; // vtはVT_BYREF|VT_UI1
short* piVal; // vtはVT_BYREF|VT_I2
long* plVal; // vtはVT_BYREF|VT_I4
float* pfltVal; // vtはVT_BYREF|VT_R4
double* pdblVal; // vtはVT_BYREF|VT_R8
VARIANT_BOOL* pboolVal; // vtはVT_BYREF|VT_BOOL
SCODE* pscode; // vtはVT_BYREF|VT_ERROR
CY* pcyVal; // vtはVT_BYREF|VT_CY
DATE* pdate; // vtはVT_BYREF|VT_DATE
BSTR* pbstrVal; // vtはVT_BYREF|VT_BSTR
IUnknown** ppunkVal; // vtはVT_BYREF|VT_UNKNOWN
IDispatch** ppdispVal; // vtはVT_BYREF|VT_DISPATCH
SAFEARRAY** pparray; // vtはVT_ARRAY|*
VARIANT* pvarVal; // vtはVT_BYREF|VT_VARIANT
void* byref // Generic ByRef
};
};
それぞれのメンバについては、MSDNライブラリの"VARIANT and VARIANTARG"を参照してください。
VARIANTにアクセスするための主要な関数には、以下のものがあります。
VariantInit ... VARIANT型の値を初期化する。
VariantClear ... VARIANT型の値をクリアする。
VariantChangeType ... VARIANT型の弁別子を変更し、それに伴い共用体の値も指定した弁別しの型に変更する。
また、VARIANTのメンバへのアクセスは、直接行なわず、以下のようなマクロを使用します。
VARIANT vData;
VariantInit ( &vData );
V_VT ( &vData ) = VT_I4;
V_I4 ( &vData ) = 10;
// ... 何らかの処理 ...
VariantClear ( &vData );
上記は、下記と同じです。
VARIANT vData;
VariantInit ( &vData );
vData.vt = VT_I4;
vData.lVal = 10;
// ... 何らかの処理 ...
VariantClear ( &vData );
しかし、名前なし共用体を使用できないコンパイラがある場合もあるので、その場合を考えてマクロを使用するのが一般的です。 |