Une question récente m'a amené à m'interroger sur les constructeurs de copies explicites. Voici un exemple de code que j'ai essayé de compiler sous Visual Studio 2005 :
struct A
{
A() {}
explicit A(const A &) {}
};
// #1 > Compilation error (expected behavior)
A retByValue()
{
return A();
}
// #2 > Compiles just fine, but why ?
void passByValue(A a)
{
}
int main()
{
A a;
A b(a); // #3 > explicit copy construction : OK (expected behavior)
A c = a; // #4 > implicit copy construction : KO (expected behavior)
// Added after multiple comments : not an error according to VS 2005.
passByValue(a);
return 0;
}
Maintenant, les questions :
- Le n°2 est-il autorisé par la norme ? Si c'est le cas, quelle est la section pertinente décrivant cette situation ?
- Connaissez-vous une utilisation pratique d'un constructeur de copie explicite ?
[EDIT] Je viens de trouver un lien amusant sur MSDN avec exactement la même situation, et un commentaire mystérieux de la fonction principale : "c est copié" (comme si c'était évident). Comme l'a souligné Oli Charlesworth : gcc ne compile pas ce code et je crois qu'il a raison de ne pas le faire.
0 votes
Je ne pense pas que les constructeurs de copies explicites soient une bonne idée. Où les avez-vous lus ?
1 votes
Cela semble être corrigé dans VC++2010 - il donne une erreur pour la ligne
passByValue(a);
.0 votes
Si vous aviez un constructeur supplémentaire pour
A
qui n'est pas explicite, par exempleA(const char*)
alors je pense que vous pouvez toujours appelerpassByValue
en passant quelque chose qui utilise ce constructeur alternatif, par exemplepassByValue("foo")
. Mais je ne suis pas assez confiant pour poster ceci comme une réponse réelle.