我的理解是,目的std::vector::emplace_back()
是避免调用复制构造函数,而是直接构造对象.
请考虑以下代码:
#include#include #include using namespace std; struct stuff { unique_ptr dummy_ptr; boost::filesystem::path dummy_path; stuff(unique_ptr && dummy_ptr_, boost::filesystem::path const & dummy_path_) : dummy_ptr(std::move(dummy_ptr_)) , dummy_path(dummy_path_) {} }; int main(int argc, const char * argv[]) { vector myvec; // Do not pass an object of type "stuff" to the "emplace_back()" function. // ... Instead, pass **arguments** that would be passed // ... to "stuff"'s constructor, // ... and expect the "stuff" object to be constructed directly in-place, // ... using the constructor that takes those arguments myvec.emplace_back(unique_ptr (new int(12)), boost::filesystem::path()); }
出于某种原因,尽管使用了该emplace_back()
函数,但此代码无法编译,错误如下:
error C2248: 'std::unique_ptr<_Ty>::unique_ptr' : cannot access private member declared in class 'std::unique_ptr<_Ty>' [...] This diagnostic occurred in the compiler generated function 'stuff::stuff(const stuff &)'
请注意,编译器尝试创建(和使用)COPY CONSTRUCTOR.正如我上面所讨论的,这是我的理解是,目的的emplace_back()
是避免使用拷贝构造函数.
当然,由于编译器试图创建并调用复制构造函数,即使我为复制构造函数定义了复制构造函数stuff
,代码也无法编译,因为std::unique_ptr
它不能在复制构造函数中使用.因此,我非常希望避免使用复制构造函数(事实上,我需要避免使用它).
(这是Windows 7 64位上的VS 11.0.60610.01 Update 3)
为什么编译器会生成并尝试使用复制构造函数,即使我正在调用emplace_back()
?
注意(回应@ Yakk的回答):
显式添加移动构造函数,如下所示,可以解决问题:
stuff(stuff && rhs) : dummy_ptr(std::move(rhs.dummy_ptr)) , dummy_path(rhs.dummy_path) {}
Yakk - Adam .. 19
Visual Studio 2013及更早版本无法为您编写默认移动构造函数.添加一个简单的显式移动构造函数stuff
.
如果需要重新分配,推送或安装后退可以导致移动东西,在您的情况下复制,因为stuff
没有移动.
这是一个msvc错误.
Visual Studio 2013及更早版本无法为您编写默认移动构造函数.添加一个简单的显式移动构造函数stuff
.
如果需要重新分配,推送或安装后退可以导致移动东西,在您的情况下复制,因为stuff
没有移动.
这是一个msvc错误.