45 votes

Quelle est la sémantique exacte d'une fonction supprimée dans C ++11?

 struct A
{
    A();

    A(const A&);
    A& operator =(const A&);

    A(A&&) = delete;
    A& operator =(A&&) = delete;
};

struct B
{
    B();

    B(const B&);
    B& operator =(const B&);    
};

int main()
{
    A a;
    a = A(); // error C2280

    B b;
    b = B(); // OK
}
 

Mon compilateur est VC ++ 2013 RC.

erreur C2280: 'A & A :: operator = (A &&)': tentative de référencer un fonction supprimée

Je me demande simplement pourquoi le compilateur n'essaie pas A& operator =(const A&); lorsque A& operator =(A&&) est supprimé?

Ce comportement est-il défini par la norme C ++?

71voto

Nawaz Points 148870
a = A(); // error C2280

L'expression de droite est temporaire, ce qui signifie qu'il va chercher operator=(A&&) et voit qu'il est supprimé. D'où l'erreur. Il n'y a pas de poursuite de la recherche.

=delete ne pas dire "ne parle pas de moi, au lieu d'utiliser la prochaine meilleur". Il signifie plutôt "ne parle pas de moi quand vous en avez besoin — au lieu d'être seul dans la nature."

Voici un autre exemple. Si je veux le cas de ma classe X être créés avec un seul long et aucun autre type (même si il se transforme en long!), ensuite, je voudrais déclarer class X comme:

struct X
{
     X(long arg); //ONLY long - NO int, short, char, double, etc!

     template<typename T>
     X(T) = delete;
};

X a(1);  //error - 1 is int 
X b(1L); //ok    - 1L is long

Cela signifie que la résolution de surcharge est effectuée avant le compilateur voit l' =delete — et donc provoque une erreur, car l' sélectionnés surcharge est trouvé supprimé.

Espérons que cela aide.

23voto

Mark Garcia Points 9851

Lorsque vous =delete d'une fonction, vous êtes effectivement la suppression de sa définition.

8.4.3 Supprimé définitions [dcl.fct.def.supprimer]

1 la définition d'Une fonction de la forme:

attribut spécificateur-seqopt decl-spécificateur-seqopt de demande de déclaration = delete ;

est appelé supprimé définition. Une fonction avec un supprimée définition est appelé aussi supprimé la fonction.

Mais en procédant ainsi, vous êtes également déclarer cette fonction. Citant le standard [1]:

4 A supprimé la fonction est implicitement en ligne. [ Note: La définition de la règle (3.2) s'applique à supprimé de définitions. -la note de fin de ] A supprimé la définition d'une fonction est la première déclaration de la fonction [...]

Et donc, en faisant a = A(), le compilateur fait résout A::operator=(A&&) parce qu'il a été déclaré (pas A::operator(const A&)car A&& "plus contraignantes" pour les valeurs r). Cependant, avec sa définition étant supprimé, la ligne est mal formé.

2 Un programme qui fait référence à une suppression de la fonction implicitement ou explicitement, d'autres que de déclarer qu'il est mal formé.


[1] Le ton de l'a souligné la phrase ici est en fait un impératif. La norme stipule que la déclaration d'une fonction =deleted doit d'abord apparaître avant les autres déclarations d'elle. Mais encore, il soutient le fait que la suppression d'une fonction, il déclare la fonction.

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