конвертировать указатель в shared_ptr - PullRequest
1 голос
/ 20 мая 2009

У меня есть некоторый библиотечный код (я не могу не изменить исходный код), который возвращает указатель на объект (B). Я хотел бы сохранить этот указатель как shared_ptr в классе с этим типом конструктора:

class A
{
  public:
   A(boost::shared_ptr<B> val);
   ...
  private:
   boost::shared_ptr<B> _val;
   ...
};

int main()
{
   B *b = SomeLib();
   A a(b); //??
   delete b;
   ...
} 

То есть я хотел бы сделать глубокую копию b и контролировать ее время жизни под a (даже если оригинал b удален (удалить b), у меня все еще есть точная копия под a).

Я новичок в этом, извините, если это кажется тривиальным ...

Ответы [ 3 ]

2 голосов
/ 20 мая 2009

Если библиотека определяет этот объект B, библиотека должна предоставить (или полностью запретить) механизм копирования B.

В качестве sidenote,

Если ваш класс A управляет исключительно временем жизни этого скопированного объекта, умный указатель, который вы действительно хотите использовать, будет boost::scoped_ptr.

boost::shared_ptr назван в честь его способности разделять пожизненную ответственность, которая, как кажется, вам не нужна. scoped_ptr не допустит, чтобы это произошло случайно.

2 голосов
/ 20 мая 2009

Как вы говорите, вы должны копировать их, а не просто указатель. Таким образом, либо B уже реализовал метод «клонирования», либо вам нужно реализовать какой-то внешний B* copy(B* b), который создаст новый B с таким же состоянием.

В случае, если B реализовал конструктор копирования, вы можете реализовать копирование как

B* copyOf(B* b)
{
    return new B(*b);
}

В случае, если B реализовал метод клонирования или аналогичный , вы можете реализовать копирование как

B* copyOf(B* b)
{
    return b->clone();
}

и тогда ваш код будет выглядеть как

int main()
{
   B *b = SomeLib();
   A a(copyOf(b));
   delete b;
   ...
}
1 голос
/ 20 мая 2009

Глубокое копирование тривиально реализуется в C ++ конструктором копирования, поскольку в C ++ все объекты имеют семантику значений по умолчанию. Копирование таким способом не работает для полиморфных объектов - в таких случаях вам придется реализовать практически переопределенный метод clone в вашем классе.

Но во всех остальных случаях просто пишу

A(boost::shared_ptr<B> val) : _val(new B(*val)) { }

будет делать.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...