如何将unique_ptr的向量声明为类数据成员?
How to declare a vector of unique_ptr's as class data member?
我想要一个unique_ptr的向量作为我正在创建的类的成员。
class Foo {
[...]
private:
vector<unique_ptr<Bar>> barList;
}
但随后我开始从VS2010编译器获得神秘的错误消息:
error C2248: 'std::unique_ptr<_Ty>::operator =' : cannot access private member declared in class 'std::unique_ptr<_Ty>'
除了下面的几条错误线,这些错误线深入探讨了微软对std::_Copy_impl<>
的实现。。。
我将会员声明改为
vector<unique_ptr<Bar>>* barList;
它进行编译。但我忍不住想知道,为什么我不能按照我最初想要的方式去做?对于咧嘴笑,我试过这个,效果很好:
vector<Bar> barList;
但现在我失去了unique_ptr
的便利性。我想要我的蛋糕,我也想吃!
这里的问题是,在某个地方,您的代码试图调用Foo
的"复制赋值"运算符。
这导致编译器尝试生成一个复制赋值运算符,该运算符调用Foo
的所有子对象的复制赋值运算符。最终,这导致了复制unique_ptr
的尝试,这是不可能的操作。
unique_ptr
没有复制语义,因此不能使用任何复制所包含对象的方法。您可以通过在它试图复制的地方使用std::move
来对右值引用执行此操作。如果没有看到你的代码,我就不能说它会在哪里。
如果它以第二种形式编译,要么你没有使用相同的代码,要么存在编译器错误。两者都应该以同样的方式失败。
第三个例子,按值存储是最简单的方法,除非您的对象很大并且按值存储/复制成本很高。
通常std::move(iUniquePtr)
在某个地方丢失(例如,使用push_back时)。
摘录自www.cplusplus.com
std::unique_ptr::operator=
unique_ptr分配对象获取x内容的所有权,包括存储的指针和存储的删除器(以及在某个时刻删除对象的责任)。unique_ptr对象在调用之前拥有的任何对象都将被删除(就好像调用了unique_ptr的析构函数一样)
但也有一个警告:
本页介绍了C++标准最新修订版(2011年)引入的一项功能。较旧的编译器可能不支持它。
MSVC 2010将operator=
定义为私有(不可复制),但支持swap
方法。
erase()
、emplace*()
和push*()
。当一个或多个矢量元素被擦除或插入时,这些将尝试四处移动矢量元素。虽然这应该起作用,但由于std::unique_ptr
是可移动的,并且不严格要求移位,所以有时它不起作用,原因是STL
实现中的错误。出于这个原因,使用std::list
可能会更好,可以使用std::shared_ptr
、使用std::vector
替代方案、提交错误,或者只使用原始指针,这是一个非常简单有效的解决方案。
不能在vector中使用unique_ptr,因为vector实现强烈依赖于值赋值运算符,该运算符在unique_ptr
中是私有的。使用boost中的shared_ptr
或C++11中的其他智能ptr实现。
- 调用在 HXX 文件中声明的静态数据成员
- 类模板静态数据成员定义/声明/初始化
- 在 C++14 中使用 decltype(auto) 声明静态数据成员
- 错误:非静态数据成员的使用无效,在此范围内未声明变量
- C++为什么 int 变量可以声明为类的私有数据成员,但不能声明为字符串变量
- 重新声明静态 constexpr 数据成员?
- 只有当声明一个对象时,内存空间才会分配给类的数据成员,那么为什么 Sizeof(class_name) 给我结果
- 静态声明的二维数组C++为类的数据成员
- C++11 - 将非静态数据成员声明为 'auto'
- 为没有数据成员和基类的类隐式声明了复制构造函数
- C++istream运算符重载-即使声明为友元,也无法访问数据成员
- 在声明数据成员之前,成员函数中数据成员的可访问性
- 声明的数组数据成员没有大小
- 我们如何能够在与类具有相同数据类型的类中声明静态成员
- 如何在函数模板中使用前向声明的数据成员?(C++)
- 如何将unique_ptr的向量声明为类数据成员?
- 声明SDL_Rect数据成员在启动时崩溃,找不到原因
- 如何区分类成员函数的声明和数据成员的声明
- c++ error:(私有数据成员)未在此范围内声明
- 数据成员是不可访问的,即使该类已声明为友元类