如何将矢量>复制到独立矢量
我有一个std::vector<std::unique_ptr<T>> vec1
其中T是一个抽象类型。我想创建std::vector<T*> vec2
,其中来自第二个向量的指针指向的对象是由第一个向量指针指向的对象的副本。如何将矢量<unique_ptr <T>>复制到独立矢量<T*>
因此,例如:*(vec1[0]) == *(vec2[0])
和vec1[0].get() != vec2[0]
...等...
如何做到这一点?
使用std::transform
std::vector<T*> vec2;
vec2.reserve(vec1.size()); // optimization to avoid reallocations, it isn't necessary, and without it the code still works correctly
std::transform(vec1.begin(), vec1.end(), std::back_inserter(vec2), [](const std::unique_ptr<T>& p){ return YourCloneFunction(*p); }
一种方法写一个克隆功能是让你的所有子类都定义的虚拟clone
功能,这在T
中是抽象的。这种方法的代码很简单,但需要为每个Derived
类定义。
class T
{
virtual std::unique_ptr<T> clone() const = 0;
virtual ~T(){}
};
class Derived : public T
{
std::unique_ptr<T> clone() const override {
return std::unique_ptr<T>(new Derived(*this));
}
};
这样,代码变得
std::vector<T*> vec2;
vec2.reserve(vec1.size()); // optimization to avoid reallocations, it isn't necessary, and without it the code still works correctly
std::transform(vec1.begin(), vec1.end(), std::back_inserter(vec2), [](const std::unique_ptr<T>& p){ return p->clone().release(); }
需要注意的是,我们有vec2
指向不受任何智能指针拥有的对象原始指针。这很糟糕,除非您将vec2
传递给接受这些指针所有权的传统函数。
否则,如果你想只有std::vector<T*>
鉴于拷贝,克隆成中间std::vector<std::unique_ptr<T>>
,然后在每个实例复制的.get()
结果std::vector<T*>
,因为它是一个副本,您应该在变换之前显示适当大小的保留行为的良好行为 – galop1n
为什么要放弃这个需求?真的没有理由在这里调用'reserve'。 – SergeyA
没有它,它是正确的,这是一个优化 – milleniumbug
手动方式:
std::vector<std::unique_ptr<T>> vec1;
std::vector<T*> vec2;
vec2.reserve(vec1.size()); // optimization to avoid reallocations
for (const auto& e : vec1) {
vec2.push_back(e->clone());
}
与virtual T* T::clone() const
究竟是什么问题?你不知道如何从'unique_ptr'获得底层指针?或者是其他东西? – SergeyA
@SergeyA。我知道很热从'std :: unique_ptr'('get()'方法)获取原始指针。但是如果我将它推到vec2那么vec2将不会独立于vec1。来自vec1的指针将指向与来自vec2的指针相同的内存位置。我需要复制对象。 – peter55555
为什么?这是一个巨大的代码气味。 C API采用'T **'和所有权? :( –