Dans l'opérateur d'assignation d'une classe, vous devez généralement vérifier si l'objet assigné est l'objet invoquant afin de ne pas tout gâcher :
Class& Class::operator=(const Class& rhs) {
if (this != &rhs) {
// do the assignment
}
return *this;
}
Avez-vous besoin de la même chose pour l'opérateur d'affectation des mouvements ? Existe-t-il une situation dans laquelle this == &rhs
serait vrai ?
? Class::operator=(Class&& rhs) {
?
}
12 votes
Sans rapport avec la question posée, et juste pour que les nouveaux utilisateurs qui lisent cette question dans le futur (car je sais que Seth le sait déjà) ne se fassent pas de fausses idées, Copie et échange est la manière correcte d'implémenter l'opérateur d'assignation de copie dans lequel vous n'avez pas besoin de vérifier l'auto-assignation et-all.
0 votes
La signature doit-elle être
const Class&&
oClass&&
?0 votes
Dans des circonstances normales, l'affectation de mouvements vers/depuis le même objet ne pourrait pas se produire. La référence rvalue signifie que vous effectuez une affectation à partir d'un objet temporaire et que rien d'autre ne devrait y faire référence. Une assertion serait peut-être plus appropriée.
5 votes
@VaughnCato :
A a; a = std::move(a);
.0 votes
@Xeo : d'accord -- je ne considérerais pas cela comme normal cependant.
11 votes
@VaughnCato en utilisant
std::move
est normal. Ensuite, il faut tenir compte de l'aliasing, et lorsque vous êtes au fond d'une pile d'appels et que vous avez une référence àT
et une autre référence àT
... allez-vous vérifier l'identité ici même ? Voulez-vous trouver le premier appel (ou les premiers appels) où le fait de documenter que vous ne pouvez pas passer le même argument deux fois prouvera statiquement que ces deux références ne s'aliaseront pas ? Ou bien allez-vous faire en sorte que l'auto-affectation fonctionne tout simplement ?2 votes
@LucDanton Je préférerais une assertion dans l'opérateur d'affectation. Si std::move était utilisé de telle manière qu'il était possible de se retrouver avec une auto-assignation de rvalue, je considérerais cela comme un bug qui devrait être corrigé.
4 votes
Un endroit où l'échange automatique est normal est à l'intérieur de l'un ou l'autre.
std::sort
ostd::shuffle
- à chaque fois que vous échangez lei
etj
d'un tableau sans vérifieri != j
premier. (std::swap
est mis en œuvre en termes d'affectation des déplacements).