Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

No op delete for unique_ptr

What would be the most concise way to pass unique_ptr a custom deleter that does nothing? I need for a JNI function I'm writing, where the C++ side expects a unique_ptr, BUT, I don't want the object held by the unique_ptr to be deleted upon exiting the JNI function - I take care of the deletion later. So I'd like to do something like:

std::unique_ptr<MyClass, noop_delete> ptr;

In one line - not with a separate function definition :-)

like image 526
Frank Avatar asked Jun 25 '15 17:06

Frank


People also ask

Can you delete a unique_ptr?

An explicit delete for a unique_ptr would be reset() . But do remember that unique_ptr are there so that you don't have to manage directly the memory they hold. That is, you should know that a unique_ptr will safely delete its underlying raw pointer once it goes out of scope.

Can a unique_ptr be copied?

A unique_ptr does not share its pointer. It cannot be copied to another unique_ptr , passed by value to a function, or used in any C++ Standard Library algorithm that requires copies to be made. A unique_ptr can only be moved.

Can you set unique_ptr to Nullptr?

It will work. unique_ptr& operator=(nullptr_t) noexcept ; Effects: reset() .

What does unique_ptr reset method do?

unique_ptr::resetReplaces the managed object. 1) Given current_ptr , the pointer that was managed by *this, performs the following actions, in this order: Saves a copy of the current pointer old_ptr = current_ptr. Overwrites the current pointer with the argument current_ptr = ptr.


1 Answers

As @101010 pointed out, that's very strange to have a std::unique_ptr with a nop deleter, since the only valuable thing std::unique_ptr has is actually the deleter. Also, you said that "C++ side expects a unique_ptr", but a std::unique_ptr with a different deleter would be a different type, and this may not work.

Nevertheless, here's the way to do it:

struct nop
{
    template <typename T>
    void operator() (T const &) const noexcept { }
};

template <typename T>
using nop_unique_ptr = std::unique_ptr<T, nop>;

Note that this nop type can be used as no-operation anywhere in place of a one-argument functor.

like image 95
lisyarus Avatar answered Sep 28 '22 18:09

lisyarus