在什么条件下我应该考虑实现移动构造函数和移动运算符? [英] Under what conditions should I be thinking about implementing a move constructor and a move operator?

查看:306
本文介绍了在什么条件下我应该考虑实现移动构造函数和移动运算符?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

对于标准复制构造函数和赋值运算符,如果我的类实现了析构函数,我总是考虑实现它们或 delete

对于新的移动构造函数移动运算符,正确的方式是考虑是否需要实现?



作为从pre-C ++ 0x转换系统的第一步,我可以只是 delete 移动构造函数移动运算符或应该将它们单独放置。

解决方案

您不会担心,因为当您用户声明一个析构函数(或12.8 / 9中列出的其他任何东西),阻止默认移动构造函数生成。因此,不会有与副本一样的风险,默认是错误的。



所以,因为第一个通行证让他们孤独。在现有代码中可能有一些位置,C ++ 11移动语义允许移动,而C ++ 03指定副本。你的类将继续被复制,如果这在C ++ 03中没有导致性能问题,那么我不能立即想到为什么它将在C ++ 11中的任何原因。如果它在C ++ 03中导致性能问题,那么你有机会修复你以前从未遇到过的代码中的错误,但这是一个机会,而不是义务; - )



如果你以后实现移动构造和赋值,它们将被移动,特别是如果你认为你的类的C ++ 11客户端不太可能使用



在C ++ 11中编写新类时,可以使用swaptimization来避免拷贝,更有可能通过值传递你的类型等等。您需要考虑和实现移动在您考虑和实现交换在C ++ 03中的相同的标准。可复制的类实现了可移动的C ++ 11概念,(就像可以在C ++ 03中复制的类可以通过 std ),因为可移动不会说明源留在什么状态 - 特别是允许不变。因此,复制有效的移动,它不一定是一个有效的,对于许多类,你会发现,不像一个好的移动或交换,一个副本可以抛出。



你可能会发现,如果你有一个析构函数(因此没有默认的移动构造函数),你必须实现move你的类,并且你有一个数据成员是可移动的,但是不可复制(因此也没有默认的复制构造函数)。这是当语音和性能都变得重要时。


For standard copy constructors and assignment operators, I always think about implementing them or deleteing the defaults out of existence, if my class implements a destructor.

For the new move constructor and move operator, what is the right way to think about whether or not an implementation is necessary?

As a first pass of transitioning a system from pre-C++0x, could I just delete the default move constructor and move operator or should I leave them alone?

解决方案

You don't have to worry about it, in the sense that when you user-declare a destructor (or anything else listed in 12.8/9), that blocks the default move constructor from being generated. So there's not the same risk as there is with copies, that the default is wrong.

So, as the first pass leave them alone. There may be places in your existing code where C++11 move semantics allow a move, whereas C++03 dictates a copy. Your class will continue to be copied, and if that caused no performance problems in C++03 then I can't immediately think of any reason why it would in C++11. If it did cause performance problems in C++03, then you have an opportunity to fix a bug in your code that you never got around to before, but that's an opportunity, not an obligation ;-)

If you later implement move construction and assignment, they will be moved, and in particular you'll want to do this if you think that C++11 clients of your class are less likely to use "swaptimization" to avoid copies, more likely to pass your type by value, etc, than C++03 clients were.

When writing new classes in C++11, you need to consider and implement move under the same criteria that you considered and implemented swap in C++03. A class that can be copied implements the C++11 concept of "movable", (much as a class that can be copied in C++03 can be swapped via the default implementation in std), because "movable" doesn't say what state the source is left in - in particular it's permitted to be unchanged. So a copy is valid as a move, it's just not necessarily an efficient one, and for many classes you'll find that unlike a "good" move or swap, a copy can throw.

You might find that you have to implement move for your classes in cases where you have a destructor (hence no default move constructor), and you also have a data member which is movable but not copyable (hence no default copy constructor either). That's when move becomes important semantically as well as for performance.

这篇关于在什么条件下我应该考虑实现移动构造函数和移动运算符?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆