215 votes

std::auto_ptr à std::unique_ptr

Avec l'arrivée de la nouvelle norme (et des parties déjà disponibles dans certains compilateurs), le nouveau type std::unique_ptr est censé remplacer std::auto_ptr .

Est-ce que leur utilisation se recoupe exactement (de sorte que je puisse faire une recherche/remplacement globale sur mon code (non pas que je le ferais, mais si je le faisais)) ou dois-je être conscient de certaines différences qui ne sont pas apparentes à la lecture de la documentation ?

De plus, s'il s'agit d'un remplacement direct, pourquoi lui donner un nouveau nom plutôt que d'améliorer simplement le nom de l'entreprise ? std::auto_ptr ?

241voto

Cubbi Points 25339

Vous ne pouvez pas effectuer une recherche/remplacement globale, car vous pouvez copier un fichier auto_ptr (avec les conséquences que l'on sait), mais un unique_ptr ne peut être que déplacée. Tout ce qui ressemble à

std::auto_ptr<int> p(new int);
std::auto_ptr<int> p2 = p; 

devra devenir au moins comme ceci

std::unique_ptr<int> p(new int);
std::unique_ptr<int> p2 = std::move(p);

En ce qui concerne les autres différences, unique_ptr peut gérer correctement les tableaux (il appellera delete[] , tandis que auto_ptr tentera d'appeler delete .

117 votes

D'autre part, le fait de faire cette recherche/remplacement n'entraînera que des erreurs de compilation, cela ne cassera pas silencieusement le code pour autant que je puisse le voir. Il est donc possible de le faire en toute sécurité, si vous corrigez manuellement les erreurs de compilation par la suite.

7 votes

@jalf : En effet, je ne vois pas de contre-exemple qui serait bien défini avec auto_ptrs et UB avec unique_ptrs.

3 votes

Il semble donc que unique_ptr soit une amélioration de auto_ptr : prise en charge des tableaux et suppression de l'ambiguïté

107voto

deft_code Points 19418

std::auto_ptr y std::unique_ptr sont incompatibles à certains égards et constituent une solution de remplacement à d'autres égards. L'absence de recherche/remplacement n'est donc pas suffisante. Cependant, après une recherche/remplacement, le fait de travailler sur les erreurs de compilation devrait permettre de tout résoudre, sauf les cas particuliers. La plupart des erreurs de compilation nécessiteront l'ajout d'un élément std::move .

  • Variable d'étendue de la fonction :
    100% compatible, tant que vous ne le passez pas par valeur à une autre fonction.
  • Type de retour :
    pas compatible à 100 % mais compatible à 99 % ne semble pas erroné.
  • Paramètre de fonction par valeur :
    100% compatible avec une mise en garde, unique_ptr doivent passer par un std::move appel. Celui-ci est simple car le compilateur se plaindra si vous ne le faites pas correctement.
  • Paramètre de fonction par référence :
    100% compatible.
  • Variable membre de la classe :
    Cette question est délicate. std::auto_ptr est diabolique. Si la classe interdit la copie, alors std::unique_ptr est un remplacement au compte-gouttes. Cependant, si vous essayez de donner à la classe une sémantique de copie raisonnable, vous devrez modifier la directive std::auto_ptr le code de manutention. C'est simple, car le compilateur se plaindra si vous ne le faites pas correctement. Si vous autorisez la copie d'une classe avec un code std::auto_ptr membre sans un code spécial, alors honte à vous et bonne chance.

En résumé, std::unique_ptr est un ensemble ininterrompu std::auto_ptr . Il interdit au moment de la compilation des comportements qui étaient souvent erreurs lors de l'utilisation d'un std::auto_ptr . Ainsi, si vous avez utilisé std::auto_ptr avec le soin nécessaire, en passant à std::unique_ptr devrait être simple. Si vous vous êtes appuyé sur std::auto_ptr vous devez de toute façon remanier votre code.

14 votes

+Les auto_ptrs ne sont utiles que pour ce que 20.4.5/3 indique qu'ils sont utiles.

11 votes

Permettez-moi d'ajouter que vous devriez, par tous les moyens, remplacer auto_ptr par unique_ptr dans votre code et corriger les erreurs de compilation. Vous seriez surpris du nombre de bogues ainsi découverts.

41voto

ValarDohaeris Points 2113

Herb Sutter propose une explication intéressante sur GotW #89 :

Qu'en est-il de l'auto_ptr ? auto_ptr est plus charitablement caractérisé comme une tentative courageuse de créer un unique_ptr avant C++ de la sémantique des déplacements. auto_ptr est désormais obsolète et ne doit pas être utilisé dans les nouveaux codes. dans un nouveau code.

Si vous avez auto_ptr dans une base de code existante, lorsque vous aurez l'occasion de le faire d'essayer de faire une recherche globale et de remplacer auto_ptr par unique_ptr ; la la grande majorité des utilisations fonctionneront de la même manière, et cela pourrait révéler (en tant que (en tant qu'erreur de compilation) ou corriger (silencieusement) un ou deux bogues que vous ne saviez pas avoir. que vous ignoriez.

En d'autres termes, même si une recherche et un remplacement globaux peuvent "casser" temporairement votre code, vous devriez quand même le faire : La correction des erreurs de compilation peut prendre un certain temps, mais elle vous épargnera beaucoup plus d'ennuis à long terme.

1 votes

Excellent lien. Merci beaucoup !

37voto

UncleBens Points 24580

AFAIK, unique_ptr n'est pas un remplacement direct. Le principal défaut qu'il corrige est le transfert implicite de propriété.

std::auto_ptr<int> a(new int(10)), b;
b = a; //implicitly transfers ownership

std::unique_ptr<int> a(new int(10)), b;
b = std::move(a); //ownership must be transferred explicitly

D'autre part, unique_ptr auront de toutes nouvelles capacités : ils pourront être stockés dans des conteneurs.

10 votes

Scott Meyers a également mentionné dans son ouvrage "Effective C++" (3ème édition), point 13 (page 64), que les conteneurs STL exigent que leur contenu présente un comportement de copie "normal", de sorte que les conteneurs de type auto_ptr ne sont pas autorisées.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X