C++ копии объектов с указателями на абстрактные классы
Рассмотрим Container
класс, который в основном хранит вектор unique_ptr
с Box
объекты и могут выполнять некоторые вычисления на них.
class Container
{
private:
std::vector<std::unique_ptr<Box> > boxes_;
public:
Container(std::vector<std::unique_ptr<Box> > &&boxes): boxes_(std::move(boxes)){}
double TotalVolume() { /* Iterate over this->boxes_ and sum */ }
};
Вот, Box
абстрактный класс, который имеет чисто виртуальный метод, такой как double Box::Volume()
,
Теперь предположим, что я создаю экземпляр контейнера в основной программе как:
std::vector<std::unique_ptr<Box> > x;
x.push_back(std::move(std::unique_ptr<Box>(new SquareBox(1.0)));
x.push_back(std::move(std::unique_ptr<Box>(new RectangularBox(1.0, 2.0, 3.0)));
Container c(x);
Как мне сделать копии c
? Я хотел бы функцию, которая делает копии основного Box
объект в boxes_
, но я думаю, что это трудно сделать с базовыми классами?
1 ответ
Один из способов сделать ваши копии - это иметь виртуальный метод "Копировать" в вашем базовом классе. Этот метод создает копию текущего объекта и возвращает (уникальный) указатель на него. Если в классе есть какие-либо содержащиеся указатели, им также понадобятся новые копии (глубокая копия).
Существуют и другие подходы. Например, вы можете проверить каждый объект в векторе, чтобы определить его тип (используя dynamic_cast
), но это некрасиво, неэффективно и очень подвержено ошибкам.