136 votes

Que puis-je faire avec un objet déplacé ?

La norme définit-elle précisément ce que je peux faire avec un objet une fois qu'il a été déplacé ? J'avais l'habitude de penser que tout ce que l'on pouvait faire avec un objet déplacé était de le détruire, mais cela ne serait pas suffisant.

Par exemple, prenons le modèle de fonction swap comme défini dans la bibliothèque standard :

template <typename T>
void swap(T& a, T& b)
{
    T c = std::move(a); // line 1
    a = std::move(b);   // line 2: assignment to moved-from object!
    b = std::move(c);   // line 3: assignment to moved-from object!
}

Il est évident qu'il doit être possible d'assigner des objets "moved-from", sinon les lignes 2 et 3 échoueraient. Alors, que puis-je faire d'autre avec les objets "moved-from" ? Où puis-je trouver ces détails dans la norme ?

(Au fait, pourquoi est-ce que T c = std::move(a); au lieu de T c(std::move(a)); dans la ligne 1)

109voto

Howard Hinnant Points 59526

17.6.5.15 [lib.types.movedfrom]

Les objets de types définis dans la bibliothèque standard C++ peuvent être déplacés de la bibliothèque standard à la bibliothèque standard. (12.8). Les opérations de déplacement peuvent être spécifiées explicitement ou générées implicitement. implicitement générées. À moins qu'il n'en soit spécifié autrement, ces objets déplacés de doivent être placés dans un état valide mais non spécifié.

Lorsqu'un objet est dans un état non spécifié, vous pouvez effectuer toute opération sur l'objet qui n'a pas de conditions préalables. Si vous souhaitez effectuer une opération avec des conditions préalables, vous ne pouvez pas l'effectuer directement car vous ne savez pas si l'état non spécifié de l'objet satisfait aux conditions préalables.

Exemples d'opérations qui généralement n'ont pas de conditions préalables :

  • destruction
  • affectation
  • get , empty , size

Exemples d'opérations qui généralement ont des conditions préalables :

  • déréférencer
  • pop_back

Cette réponse apparaît maintenant en format vidéo ici : http://www.youtube.com/watch?v=vLinb2fgkHk&t=47m10s

52voto

Puppy Points 90818

Les objets "Moved-from" existent dans un état non spécifié, mais valide. Cela suggère que, même si l'objet n'est plus capable de faire grand-chose, toutes ses fonctions membres devraient encore avoir un comportement défini, notamment operator= - et tous ses membres dans un état défini et il faut encore le détruire. La norme ne donne aucune définition spécifique car elle serait propre à chaque UDT, mais vous pourriez trouver des spécifications pour les types standard. Certains, comme les conteneurs, sont relativement évidents - ils déplacent simplement leur contenu et un conteneur vide est un état valide bien défini. Les primitives ne modifient pas l'objet déplacé.

Remarque : je crois que c'est T c = std::move(a) de sorte que si le constructeur de déplacement (ou le constructeur de copie si aucun déplacement n'est fourni) est explicite, la fonction échouera.

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