version courte: em> version longue: em> La question est donc la suivante: existe-t-il une telle chose que sur l'utilisation des pointeurs intelligents?
Existe-t-il des raisons acceptables pour utiliser des pointeurs non intelligents dans le C ++ moderne? P>
Nous avons un énorme produit contenant du lot d'ancien code C ++ et nous essayons maintenant de le refroidir à l'époque moderne C ++. En plus de tout le code à l'ancienne, il y a une énorme quantité de pointeurs qui passent autour (principalement avec des annotations salutes pour donner un certain sens de la sécurité) et je me demandais si nous devions tous les changer à des pointeurs intelligents ou peut-être laisser certains d'entre eux comme c'est ?
En essayant de convertir certains de ces codes, j'ai fini avec un code qui est simplement argumenté pour sur l'utilisation des pointeurs intelligents forts>. p>
Ou en d'autres termes: existe-t-il un scénario acceptable pour des pointeurs non intelligents ces jours-ci? P>
5 Réponses :
Consultez les pourparlers ici: http://channel9.msdn.com/events/undnative/ 2013 (surtout Stroustrup's Talk). P>
La réponse courte est non, en supposant que "moderne C ++" est> = C ++ 11 P>
La longue réponse est que ce n'était pas toujours le cas et essayant de restructurer un grand projet est presque toujours difficile. La façon dont nous pensons que les problèmes sont contraints par les outils que nous devons les résoudre. Il y a beaucoup de cas lors de ce refactoring lorsqu'il est tout simplement logique d'utiliser des pointeurs que d'essayer de réexprimer la logique de base pour être la classe et le pointeur intelligent. Je pense que c'est moins un cas où les pointeurs intelligents sont surutilisés et plus d'une affaire lorsque des cours sont utilisés. Ymmv; -) p>
um qu'est-ce que "moderne C ++" est> = C ++ 11 signifie
@aaronman "en supposant que par" moderne c ++ '"signifie C ++ 11 ou plus tard"
MEH, il reste encore près de zéro excuses pour écrire le code Bad en C ++ 03.
Pointeurs intelligents ( Les méthodes d'usine doivent renvoyer et consultez la réponse d'Ali concernant des liens vers certains points philosophiques de la gestion du code hérité. (Que je suis totalement d'accord sur) p> unique_ptr code> et
partagé_ptr code>) devrait être posséder des pointeurs (c'est-à-dire responsables de la destruction de l'objet). La dernière ligne de l'utilisation est que tout objet créé par
nouveau code> doit être poussé dans un
unique_ptr code> dès que possible, pour éviter les fuites de mémoire. Après cela, le
unique_ptr code> devrait finir par être déplacé: p>
partagé_ptr code> si la propriété doit être partagée, LI>
unique_ptr code> si la propriété est déterminée par une portée (d'un bloc ou de la durée de vie d'un objet). LI>
ul>
libération code> s doit être rare. Si votre code transmet des pointeurs non propriétaires, ceux-ci devraient être: p>
null code>, (obtenu par
obtenez code>) li>
null code>, (obtenu par
obtenir code>) li>
unique_ptr code> S par valeur si le but de l'appel transfère la propriété. (Dans ce cas, vous aurez besoin de les déplacer) li>
ul>
unique_ptr code> S par valeur. (Parce que, si vous n'édérez pas la valeur de retour de la méthode d'usine, l'objet est immédiatement désaffecté) P>
Oui, les pointeurs bruts ont toujours une utilisation comme une "référence facultative". C'est à dire. Un t * code> est similaire à un
t & code>. Ni implique la propriété, mais un
t * code> peut être un
nullptr code>. P>
Mais il y a sûrement des alternatives plus sûres que les pointeurs bruts pour cela? Je pense à Boost's (désormais aussi std :: expérimental) en option code> car il est clair ce qui se passe, mais même juste des pointeurs intelligents eux-mêmes peuvent être utilisés de cette manière.
@Jimmidyjoo: Ouais, j'ai fait le exactement la même observation a > hier
Bien sûr, il existe des cas d'utilisation pour les pointeurs bruts de moderne C ++: p>
Bien sûr, ce sont des cas plutôt rares et de loin les cas les plus utilisés des pointeurs intelligents des pointeurs doivent être très bien pour le nouveau code, mais: P>
Si le code existant fonctionne bien avec des pointeurs bruts, pourquoi investir du temps pour la réécrire et le risque d'ajouter des bugs lors de la conversion d'un pointeur intelligent à l'aide de la version? P>
Ne pas le refacteur du code, cela fonctionne bien, simplement parce que le nouveau code suit mieux les normes de programmation modernes. Ces normes de programmation n'existent pas pour eux-mêmes, mais pour faciliter le travail avec certains codes, alors ne vous refactez pas, ce qui vous coûtera plus de temps que ce qu'ils ne peuvent vous sauver à l'avenir. P>
Cela signifie: Si cela vous coûtera plus de temps pour vérifier, lequel de ces pointeurs peut être converti en toute sécurité en pointes intelligents et qui ne peuvent pas et pour chasser les bugs, que votre refactoring a peut-être introduit que vous ne serez pas capable d'économiser sur les travaux de maintenance futurs en raison du refactoring, alors ne refactez-vous simplement pas et laissez-le rester tel qu'il est. P>
Si le refactoring économisera plus de temps qu'il ne coûte que certaines parties de la base de code, envisagez de refroidir uniquement ces parties de la base de code. P>
version courte: em>
Y a-t-il des raisons acceptables pour utiliser non intelligemment Pointeurs dans le C ++ moderne? P> blockQuote>réponse courte: em> p>
Certainement, s'ils ne servent que pour l'observation, c'est-à-dire
ils ne possèdent pas strong> le pointee. Cependant, essayez d'utiliser des références au lieu des pointeurs même dans ce cas; Utilisez des pointeurs uniquement si vous devez vraiment les faire facultatif (initialiser avec null_ptr code> puis réaffectage ultérieurement, par exemple). P>
version longue: em>
Nous avons un énorme produit contenant du lot d'ancien code C ++ et nous essayons maintenant de le refroidir à l'époque moderne C ++. [...] p> blockQuote>réponse longue: em> p>
Comme je lis ces lignes, cette réponse me vient à l'esprit: p>
- Conseils sur le travail avec le code hérité Li> ul>
J'aimerais pouvoir uppouver cette réponse plus d'une fois. Je citerais: "[...] pour chaque re-facteur que nous avons fait que nous puissions justifier" ce changement spécifique fera la tâche réelle que nous faisons maintenant plus facile ". Plutôt que" C'est maintenant plus propre pour les travaux futurs '. " em> p>
Longue histoire courte, ne faites pas grand refactoring à moins que vous n'ayez vraiment besoin. P>
La question est donc la suivante: existe-t-il une telle chose que sur l'utilisation des pointeurs intelligents? P> blockQuote>
à mon avis,
std :: partagé_ptr code> est surutilisé. Il est très confortable à utiliser et cela vous donne l'illusion que vous n'avez pas à réfléchir aux problèmes de propriété. Mais ce n'est pas la photo entière. Je suis tout à fait d'accord avec Sean Parent : "Un pointeur partagé est aussi bon qu'une variable globale. " EM> Les pointeurs partagés peuvent également introduire des problèmes de propriété très difficiles, etc. p>
D'autre part, si vous devez attribuer quelque chose sur le tas, utilisez un
unique_ptr code>. Vous ne pouvez pas l'exclure, si vous vraiment em> avez besoin d'une allocation de tas. Dans mon expérience, en utilisant
unique_ptr code> conduit également à un nettoyant et plus facile à comprendre le code, car les problèmes de propriété deviennent explicatifs auto-explicatifs. P>
Des discussions intéressantes de Sean Parent sur la façon d'éviter / réduire l'utilisation des pointeurs sont les suivants: P>
Valeur Sémantique et polymorphisme basé sur les concepts P> < / li> ul>
J'espère que cela aide. P>
S'ils ne possèdent rien, il n'y a pas beaucoup de point.
Le problème est qu'elles n'auraient probablement pas dû être des indications du tout (premiers points de cœur », n'a pas beaucoup de place dans le C ++ moderne, comme vous l'avez dit), mais aussi si ce n'est pas cassé, ne le répare pas
Les pointeurs bruts sont corrects en C ++ moderne s'ils ne possèdent aucune ressource. Ce n'est pas nécessaire que vous ne devez pas modifier tous les pointeurs bruts en pointes intelligents.