复制具有 const 向量成员的 class 的构造函数

Copy constructor of a class with a const vector member

我的代码中有 class OpenTable

class OpenTable : public BaseAction {
public:
    OpenTable(int id, std::vector<Customer *> &customersList);
    OpenTable(const OpenTable& other);
private:
    const int tableId;
    const std::vector<Customer *> customers;
};

我需要为此 class 实现一个复制构造函数(我知道这可能是一个糟糕的设计,但我被指示这样做)。我 运行 在尝试深度复制 const 向量时遇到问题 customers

我尝试了以下方法:

OpenTable::OpenTable(const OpenTable& other): tableId(other.tableId)
{
    for(std::vector<Customer*>::const_iterator i=other.customers.begin(); i!=other.customers.end(); i++) {
         customers.push_back((*i)->copy()); // copy returns a Customer*
    }

但是很明显编译不了,可能是因为vector是const,所以我不能给它添加元素。

我收到以下错误:

no instance of overloaded function "std::vector<_Tp, _Alloc>::push_back 
[with _Tp=Customer *, _Alloc=std::allocator<Customer *>]" matches the 
argument list and object (the object has type qualifiers that prevent a 
match) -- argument types are: (Customer *) -- object type is: const 
std::vector<Customer *, std::allocator<Customer *>>

注意:在参数化构造函数中,我只是浅复制,因为我可以。不过,这对复制构造函数不起作用。

提前致谢。

作为成员初始化程序的一部分,您将需要 boost::transform_iterator 之类的东西来进行复制。

auto copy_iter(auto iter)
{
    return boost::make_transform_iterator(iter, [](Customer * c){ return c->copy(); });
}

OpenTable::OpenTable(const OpenTable& other)
 : tableId(other.tableId),
   customers(copy_iter(other.customers.begin()), copy_iter(other.customers.end()))
{}

或者

OpenTable::OpenTable(const OpenTable& other)
 : tableId(other.tableId),
   customers(boost::copy_range<std::vector<Customer *>>(other.customers | boost::adaptors::transformed([](Customer * c){ return c->copy(); })))
{}

为什么要使用 const class 成员?你对他们无能为力。改为只读访问 public 访问函数。

std::vector<Customers *> const getCustumers() const { return customers;}
int const getTableId() const { return tableId; }

这将为您提供客户的只读矢量或无法修改的 table ID。比copy constuctor没问题。

最简单的解决方案是创建一个辅助函数,它接受一个 const std::vector<Customer *> 和 returns 一个 std::vector<Customer *>,这是参数的深层副本。然后,在构造函数的初始化列表中,使用该函数初始化您的私有成员。

可选地,如果您想限制对它的访问,该辅助函数可以是 class 的 privatestatic 成员。这在构造函数或其初始化列表中是可以接受的,因为 static 成员函数不依赖于 class 的非静态成员被初始化,因此不依赖于构造函数已经完成。

如果在进行深拷贝的辅助函数中出现问题,辅助函数将需要适当清理(例如,如果 Customer 对象之一的构造失败,任何成功构造的对象都需要被释放以避免内存泄漏)。