Lors de l'implémentation d'une interface COM
, j'attribue toujours les paramètres out en cas de succès mais devrais-je le faire également en cas d'erreur?Les paramètres de sortie doivent-ils être définis même si la fonction COM échoue?
HRESULT CDemo::Div(/*[in]*/ LONG a, /*[in]*/LONG b, /*[out,retval]*/ LONG* pRet)
{
if (pRet == NULL)
return E_POINTER;
if (b == 0)
{
*pRet = 0; // is this redundant?
return E_INVALIDARG;
}
*pRet = a/b;
return S_OK;
}
À un moment donné, j'étais un peu sur le nez de ne pas initialiser un paramètre out et en supposant que si j'initialisés la variable il reste que la valeur si je ne change pas à l'intérieur de la méthode. Cependant, j'ai utilisé cette méthode de .NET
et puisque le marshaller voit que c'est un paramètre [out]
il a rejeté la valeur initiale que j'ai placé sur le site d'appel et mis dans la poubelle après la fonction retournée (c'était amusant de déboguer cela, pas).
Attribue un out
param même en cas de surcompensation de panne ou devrais-je vraiment le faire?
Edit: Même si on ne doit pas accéder formellement à params si la fonction a échoué, je vois souvent (et parfois écrire) code comme ceci (en utilisant l'exemple de sharptooth's post):
ISmth *pSmth = NULL;
pObj->GetSmth(&pSmth); // HRES is ignored
if (pSmth) // Assumes that if GetSmth failed then pSmth is still NULL
{
pSmth->Foo();
pSmth->Release();
}
Cela fonctionne bien dans le code non-marshalled (même thread apartment) mais si un marshaller est impliqué est-il assez intelligent pour seulement définir la valeur de retour si la fonction a réussi?
Je pense que cela ne devrait pas avoir d'importance. Le client COM appelant ne doit pas regarder le paramètre 'out' en cas d'échec. –