У меня есть функции, которые принимают в std:: shared_ptr как аргумент, поэтому я вынужден использовать std:: shared_ptr, но объект, который я передаю функции, не выделяется динамически. Как обернуть объект в std:: shared_ptr и удалить std:: shared_ptr, но не удалить его.
Как вы делаете std:: shared_ptr не вызывать delete()
Ответ 1
MyType t;
nasty_function(std::shared_ptr<MyType>(&t, [](MyType*){}));
Ответ 2
Задание отсутствия операции при создании общего указателя. Например. например:
void null_deleter(MyType *) {}
int main()
{
MyType t;
nasty_function(std::shared_ptr<MyType>(&t, &null_deleter));
}
Ответ 3
Лучший способ сделать это - использовать конструктор псевдонимов:
nasty_function(std::shared_ptr<MyType>(std::shared_ptr<MyType>{}, &t));
По сравнению с подходом с нулевым удалением это не нужно выделять блок управления и noexcept
.
Как отмечено @Casey и @Nevin, это должно быть сделано только тогда, когда вы уверены, что функция не будет пытаться использовать совместное владение, или если объект будет переживать все, что может "владеть" им.
Ответ 4
Вы можете сделать этот трюк:
A a;
shared_ptr<A> pa(&a);
foo(pa);
new (&pa) shared_ptr<A>(); // pa "forgets" about a
Ответ 5
Я просто искал решение, увидел этот вопрос. ничего не нашел и сделал отличный, это мой код
class HBitmap : public shared_ptr<HBITMAP__>
{
public:
HBitmap();
HBitmap(HBITMAP Handle);
bool autoDelete = true;
};
Win32::HBitmap::HBitmap(HBITMAP Handle)
: shared_ptr<HBITMAP__>(Handle, [&](HBITMAP hBitmap) {if(autoDelete)DeleteObject(hBitmap);})
{
}
это решение представляет собой комбинацию лямбда-выражений и наследования.
очень хорошо сформировался. быстро. вы не можете ожидать ничего большего. не только вы можете установить дебетер, но если вы внесете некоторые изменения, вы можете использовать std::function<void(pointer)>
в качестве пользовательского делетера. с lambdas вы можете бежать бесплатно и делать то, что вы хотите.