Question

Voici le code que je souhaite accélérer. Obtenir une valeur d'un jeu d'enregistrements ADO et la convertir en un caractère *. Mais c'est lent. Puis-je ignorer la création de _bstr_t?

                _variant_t var = pRs->Fields->GetItem(i)->GetValue();

                if (V_VT(&var) == VT_BSTR)
                {
                    char* p = (const char*) (_bstr_t) var;
Était-ce utile?

La solution

Les 4 premiers octets du BSTR contiennent la longueur. Vous pouvez passer en boucle et obtenir tous les autres caractères si Unicode ou tous les caractères si plusieurs octets. Une sorte de mémoire ou une autre méthode fonctionnerait aussi. IIRC, cela peut être plus rapide que W2A ou transtyper (LPCSTR) (_ bstr_t)

Autres conseils

Votre problème (autre que la possibilité d'une copie de mémoire dans _bstr_t) est que vous convertissez le BSTR UNICODE en un caractère ANSI *.

Vous pouvez utiliser les macros USES_CONVERSION qui effectuent la conversion sur la pile afin d’être plus rapides. Sinon, conservez la valeur BSTR au format Unicode si possible.

convertir:

USES_CONVERSION;
char* p = strdup(OLE2A(var.bstrVal));

// ...

free(p);

rappelez-vous - la chaîne renvoyée par OLE2A (et ses macros sœurs) renvoie une chaîne allouée sur la pile - renvoie de la portée englobante et que vous avez une chaîne erronée à moins que vous ne la copiez (et la libérez éventuellement, évidemment)

Ceci crée un temporaire sur la pile:

USES_CONVERSION;
char *p=W2A(var.bstrVal);

Ceci utilise une syntaxe légèrement plus récente et est probablement plus robuste. Il a une taille configurable, au-delà de laquelle il utilisera le tas, évitant ainsi de mettre des chaînes énormes sur la pile:

char *p=CW2AEX<>(var.bstrVal);
_variant_t var = pRs->Fields->GetItem(i)->GetValue(); 

Vous pouvez également rendre cette affectation plus rapide en évitant la collecte de champs dans son ensemble. Vous ne devez utiliser la collection Fields que lorsque vous devez récupérer l'élément par son nom. Si vous connaissez les champs par index, vous pouvez plutôt utiliser ceci.

_variant_t vara = pRs->Collect[i]->Value;

Remarque: je ne peux pas être un entier, ADO ne prenant pas en charge VT_INTEGER, vous pouvez donc également utiliser une variable longue.

D'accord, mon C ++ rouille un peu ... mais je ne pense pas que la conversion soit votre problème. Cette conversion ne fait vraiment rien sauf dire au compilateur de considérer _bstr_t un char *. Ensuite, vous n'attribuez que l'adresse de ce pointeur à p. Rien n'est réellement "fait".

Êtes-vous sûr que ce n'est pas seulement lent de recevoir des informations de GetValue?

Ou est-ce que mon C ++ est plus rustique que je ne le pense ...

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top