Безоперационный диллокатор для boost :: shared_ptr - PullRequest
17 голосов
/ 26 апреля 2010

Есть ли в Boost серийный бездействующий деаллокатор, который можно использовать с boost::shared_ptr для статических объектов и т. Д.

Я знаю, что писать это очень тривиально, но я не хочу обсыпать свой код дополнительными крошечными функциями, если он уже есть.

Ответы [ 6 ]

10 голосов
/ 08 марта 2011

Да, здесь есть один:

#include <boost/serialization/shared_ptr.hpp> // for null_deleter

class Foo
{
  int x;
};

Foo foo;
boost::shared_ptr< Foo > sharedfoo( &foo, boost::serialization::null_deleter() );

Разумеется, существует опасность того, что вам нужно знать, что вызываемая вами функция не хранит shared_ptr для последующего использования, поскольку это фактически противоречит политике shared_ptr, поскольку базовый объект остается действительным до тех пор, пока последний экземпляр shared_ptr.

3 голосов
/ 26 апреля 2010

Решение использует Boost.Lambda:

#include <boost/shared_ptr.hpp>
#include <boost/lambda/lambda.hpp>

int main()
{
    int *p = new int(5);

    {
        boost::shared_ptr<int> sp(p, boost::lambda::_1);
    }

    delete p;
}

'boost :: lambda :: _ 1' создает пустой функтор, который принимает один аргумент.

Вы, вероятно, захотите разместить там // комментарий, чтобы люди знали, почему вы это сделали.

1 голос
/ 08 марта 2011

Для отслеживания ошибок в Boost есть билет: https://svn.boost.org/trac/boost/ticket/1913 - долгое время не было никаких действий, пока две недели назад не было шума.

1 голос
/ 26 апреля 2010

Разве не было бы чище просто взять дополнительную ссылку, чтобы не вызывать деллокатор? (Хотя это все еще не очень чисто.)

Я не могу сказать, что в Boost нет функции, которая бы выполняла эту работу, но это не похоже на то, что они хотели бы включить.

РЕДАКТИРОВАТЬ: Прочитав комментарии и небольшую документацию, сводится к следующему:

  1. Ссылка течет. В какой-то момент выполните это:

    new shared_ptr( my_global_shared_ptr );
    

    Преимущества: концептуально легко. Недостатки: вы что-то пропускаете в кучу.

  2. Пользовательский дилер-локатор. Так как shared_ptr требует немного функции деаллокатора, анонимная функция идентификации, подобная той, что приведена в другом ответе, подойдет.

    Преимущества: использует Boost и не имеет никаких накладных расходов. Недостатки: требуется немного документации.

  3. Нестатический глобальный объект. Если для вашего объекта есть глобальный shared_ptr, это должно быть единственным средством доступа к нему. Замените объявление global на shared_ptr, инициализированное на new my_class. Я думаю, что это лучше.

0 голосов
/ 30 января 2016
0 голосов
/ 25 декабря 2011

FWIW, это то, что я использую. Я использую его в модульных тестах, чтобы адаптировать локальный в shared_ptr.

// The class NoOp_sptr_Deleter can be used to construct a shared_ptr<>()
// that will NOT delete the pointee.
// This can be helpful in unit-testing. Wrapping a local as a shared_ptr.
// Do take care with the lifetimes though.
struct NoOp_sptr_Deleter
{
    void operator()(void const *) const {}
};

template<typename T>
boost::shared_ptr<T> FakeSharedPtrFromRef(T& aRef)
{
    return boost::shared_ptr<T>(&aRef, NoOp_sptr_Deleter() );
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...