¿Cómo puedo mostrar los valores de esta instancia VARIANT y guardarlos dentro de una TStringLi? ¿S t?
El COM VARIANT
estructura tiene parray
y pparray
miembros de datos que son punteros a un SAFEARRAY
, por ejemplo:
VARIANT V;
LPSAFEARRAY sa = V_ISBYREF(&V) ? V_ARRAYREF(&V) : V_ARRAY(&V);
La clase VCL Variant
, por el contrario, tiene un operador LPSAFEARRAY
conversión definido, por lo que puede asignarlo directamente (pero solo si el campo Variant.VType
que no tiene el indicador varByRef
presente, es decir), por ejemplo:
Variant V;
LPSAFEARRAY sa = V;
De cualquier manera, una vez que tenga el puntero SAFEARRAY
, utilice la API SafeArray acceder a los valores de BSTR
, por ejemplo:
bool __fastcall VariantToStrings(const Variant &V, TStrings *List)
{
// make sure the Variant is holding an array
if (!V_ISARRAY(&V)) return false;
// get the array pointer
LPSAFEARRAY sa = V_ISBYREF(&V) ? V_ARRAYREF(&V) : V_ARRAY(&V);
// make sure the array is holding BSTR values
VARTYPE vt;
if (FAILED(SafeArrayGetVartype(sa, &vt))) return false;
if (vt != VT_BSTR) return false;
// make sure the array has only 1 dimension
if (SafeArrayGetDim(sa) != 1) return false;
// get the bounds of the array's sole dimension
LONG lBound = -1, uBound = -1;
if (FAILED(SafeArrayGetLBound(sa, 0, &lBound))) return false;
if (FAILED(SafeArrayGetUBound(sa, 0, &uBound))) return false;
if ((lBound > -1) && (uBound > -1))
{
// access the raw data of the array
BSTR *values = NULL;
if (FAILED(SafeArrayAccessData(sa, (void**)&values))) return false;
try
{
List->BeginUpdate();
try
{
// loop through the array adding the elements to the list
for (LONG idx = lBound; l <= uBound; ++idx)
{
String s;
if (values[idx] != NULL)
s = String(values[idx], SysStringLen(values[idx]));
List->Add(s);
}
}
__finally
{
List->EndUpdate();
}
}
__finally
{
// unaccess the raw data of the array
SafeArrayUnaccessData(sa);
}
}
return true;
}
VarClear (V); TVarData (V) .VType = varOleStr;
No es necesario en absoluto. La clase VCL Variant
se inicializa en un estado en blanco, y no hay necesidad de asignar VType
ya que está asignando un nuevo valor a Variant
inmediatamente después.
V = ComFunction-> GetValues (); // < < < < V ----- está vacía
Si V está vacío, entonces GetValues()
devuelve un vacío Variant
para empezar.
mystr = (wchar_t *) (TVarData (V) .VString);
TVarData::VString
es una referencia AnsiString&
, no un puntero wchar_t*
. Para convertir un VCL Variant
(no es un COM VARIANT
) a un String
, simplemente asignarla como está y dejar que el RTL funciona el detalle para usted:
String mystr = V;