22.5 — std::unique_ptr

The compiler is given a lot of flexibility in terms of how it handles this call. It could create a new T, then call function_that_can_throw_exception(), then create the std::unique_ptr that manages the dynamically allocated T. If function_that_can_throw_exception() throws an exception, then the T that was allocated will not be deallocated, because the smart pointer to do the deallocation hasn’t been created yet. This leads to T being leaked.

In the above code, createResource() returns a std::unique_ptr by value. If this value is not assigned to anything, the temporary return value will go out of scope and the Resource will be cleaned up. If it is assigned (as shown in main()), in C++14 or earlier, move semantics will be employed to transfer the Resource from the return value to the object assigned to (in the above example, ptr), and in C++17 or newer, the return will be elided. This makes returning a resource by std::unique_ptr much safer than returning raw pointers!

  • <cassert> (assert.h)
  • <cctype> (ctype.h)
  • <cerrno> (errno.h)
  • C++11 <cfenv> (fenv.h)
  • <cfloat> (float.h)
  • C++11 <cinttypes> (inttypes.h)
  • <ciso646> (iso646.h)
  • <climits> (limits.h)
  • <clocale> (locale.h)
  • <cmath> (math.h)
  • <csetjmp> (setjmp.h)
  • <csignal> (signal.h)
  • <cstdarg> (stdarg.h)
  • C++11 <cstdbool> (stdbool.h)
  • <cstddef> (stddef.h)
  • C++11 <cstdint> (stdint.h)
  • <cstdio> (stdio.h)
  • <cstdlib> (stdlib.h)
  • <cstring> (string.h)
  • C++11 <ctgmath> (tgmath.h)
  • <ctime> (time.h)
  • C++11 <cuchar> (uchar.h)
  • <cwchar> (wchar.h)
  • <cwctype> (wctype.h)

Containers:

  • C++11 <array>
  • <deque>
  • C++11 <forward_list>
  • <list>
  • <map>
  • <queue>
  • <set>
  • <stack>
  • C++11 <unordered_map>
  • C++11 <unordered_set>
  • <vector>

Input/Output:

  • <fstream>
  • <iomanip>
  • <ios>
  • <iosfwd>
  • <iostream>
  • <istream>
  • <ostream>
  • <sstream>
  • <streambuf>

Multi-threading:

  • C++11 <atomic>
  • C++11 <condition_variable>
  • C++11 <future>
  • C++11 <mutex>
  • C++11 <thread>
  • <algorithm>
  • <bitset>
  • C++11 <chrono>
  • C++11 <codecvt>
  • <complex>
  • <exception>
  • <functional>
  • C++11 <initializer_list>
  • <iterator>
  • <limits>
  • <locale>
  • <memory>
  • <new>
  • <numeric>
  • C++11 <random>
  • C++11 <ratio>
  • C++11 <regex>
  • <stdexcept>
  • <string>
  • C++11 <system_error>
  • C++11 <tuple>
  • C++11 <type_traits>
  • C++11 <typeindex>
  • <typeinfo>
  • <utility>
  • <valarray>
  • C++11 allocator_arg_t
  • C++11 allocator_traits
  • auto_ptr_ref
  • C++11 bad_weak_ptr
  • C++11 default_delete
  • C++11 enable_shared_from_this
  • C++11 owner_less
  • C++11 pointer_traits
  • raw_storage_iterator
  • C++11 shared_ptr
  • C++11 unique_ptr
  • C++11 uses_allocator
  • C++11 weak_ptr

enum classes

  • C++11 pointer_safety
  • C++11 addressof
  • C++11 align
  • C++11 allocate_shared
  • C++11 const_pointer_cast
  • C++11 declare_no_pointers
  • C++11 declare_reachable
  • C++11 dynamic_pointer_cast
  • C++11 get_deleter
  • C++11 get_pointer_safety
  • get_temporary_buffer
  • C++11 make_shared
  • return_temporary_buffer
  • C++11 static_pointer_cast
  • C++11 undeclare_no_pointers
  • C++11 undeclare_reachable
  • uninitialized_copy
  • C++11 uninitialized_copy_n
  • uninitialized_fill
  • uninitialized_fill_n
  • C++11 allocator_arg
  • C++11 unique_ptr::~unique_ptr
  • C++11 unique_ptr::unique_ptr

member functions

  • C++11 unique_ptr::get
  • C++11 unique_ptr::get_deleter
  • C++11 unique_ptr::operator bool
  • C++11 /" title="unique_ptr::operator->"> unique_ptr::operator->
  • C++11 unique_ptr::operator[]
  • C++11 unique_ptr::operator*
  • C++11 unique_ptr::operator=
  • C++11 unique_ptr::release
  • C++11 unique_ptr::reset
  • C++11 unique_ptr::swap

non-member overloads

  • C++11 relational operators (unique_ptr)
  • C++11 swap (unique_ptr)

std:: unique_ptr ::operator=

move assignment (1)
assign null pointer (2)
type-cast assignment (3)
copy assignment (deleted!) (4)
  • lhs owns the data previously owned by rhs and has rhs 's former stored pointer and stored deleter .
  • The data owned by lhs before the call has been deleted (using the deleter that member get_deleter would provide before the call).

Return value

main () { std::unique_ptr< > foo; std::unique_ptr< > bar; foo = std::unique_ptr< >( (101)); bar = std::move(foo); std::cout << ; (foo) std::cout << *foo << ; std::cout << ; std::cout << ; (bar) std::cout << *bar << ; std::cout << ; 0; }

This browser is no longer supported.

Upgrade to Microsoft Edge to take advantage of the latest features, security updates, and technical support.

How to: Create and use unique_ptr instances

  • 8 contributors

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. This means that the ownership of the memory resource is transferred to another unique_ptr and the original unique_ptr no longer owns it. We recommend that you restrict an object to one owner, because multiple ownership adds complexity to the program logic. Therefore, when you need a smart pointer for a plain C++ object, use unique_ptr , and when you construct a unique_ptr , use the make_unique helper function.

The following diagram illustrates the transfer of ownership between two unique_ptr instances.

Diagram that shows moving the ownership of a unique pointer.

unique_ptr is defined in the <memory> header in the C++ Standard Library. It is exactly as efficient as a raw pointer and can be used in C++ Standard Library containers. The addition of unique_ptr instances to C++ Standard Library containers is efficient because the move constructor of the unique_ptr eliminates the need for a copy operation.

The following example shows how to create unique_ptr instances and pass them between functions.

These examples demonstrate this basic characteristic of unique_ptr : it can be moved, but not copied. "Moving" transfers ownership to a new unique_ptr and resets the old unique_ptr .

The following example shows how to create unique_ptr instances and use them in a vector.

In the range for loop, notice that the unique_ptr is passed by reference. If you try to pass by value here, the compiler will throw an error because the unique_ptr copy constructor is deleted.

The following example shows how to initialize a unique_ptr that is a class member.

You can use make_unique to create a unique_ptr to an array, but you cannot use make_unique to initialize the array elements.

For more examples, see make_unique .

Smart Pointers (Modern C++) make_unique

Was this page helpful?

Coming soon: Throughout 2024 we will be phasing out GitHub Issues as the feedback mechanism for content and replacing it with a new feedback system. For more information see: https://aka.ms/ContentUserFeedback .

Submit and view feedback for

Additional resources

Understanding unique_ptr with Example in C++11

The smart pointers are a really good mechanism to manage dynamically allocated resources. In this article, we will see unique_ptr with example in C++11. But we don’t discuss standard smart pointers from a library. Rather, we implement our own smart pointer equivalent to it. This will give us an idea of inside working of smart pointers.

Prior to C++11, the standard provided std::auto_ptr . Which had some limitations. But from C++11, standard provided many smart pointers classes. Understanding unique_ptr with example in C++ requires an understanding of move semantics which I have discussed here & here .

But before all these nuisances, we will see “Why do we need smart pointer in 1st place?”:

Why do we need smart pointers? #

func() { Resource *ptr = new Resource; int x; std::cout << "Enter an integer: "; std::cin >> x; if (x == 0) throw 0; // the function returns early, and ptr won't be deleted! if (x < 0) return; // the function returns early, and ptr won't be deleted! // do stuff with ptr here delete ptr; }
  • In the above code, the early return or throw statement, causing the function to terminate without variable ptr being deleted.
  • Consequently, the memory allocated for variable ptr is now leaked (and leaked again every time this function is called and returns early).
  • These kinds of issues occur because pointer variables have no inherent mechanism to clean up after themselves.
  • Following class cleans-up automatically when sources are no longer in use:

smart_ptr aka std::auto_ptr from C++98 #

<class T> class smart_ptr { T* m_ptr; public: smart_ptr(T* ptr=nullptr):m_ptr(ptr){} ~smart_ptr() { delete m_ptr; } T& operator*() const { return *m_ptr; } T* operator->() const { return m_ptr; } };
  • Now, let’s go back to our func() example above, and show how a smart pointer class can solve our challenge:
Resource { public: Resource() { std::cout << "Resource acquired\n"; } ~Resource() { std::cout << "Resource destroyed\n"; } }; void func() { smart_ptr<Resource> ptr(new Resource); // ptr now owns the Resource int x; std::cout << "Enter an integer: "; std::cin >> x; if (x == 0) throw 0; if (x < 0) return; // do stuff with ptr here // dont care about deallocation } int main() { try{ func(); } catch(int val){} return 0; }
Hi! Resource destroyed
  • Note that even in the case where the user enters zero and the function terminates early, the Resource is still properly deallocated.
  • Because of the ptr variable is a local variable. ptr destroys when the function terminates (regardless of how it terminates). And because of the smart_ptr destructor will clean up the Resource , we are assured that the Resource will be properly cleaned up.
  • There is still some problem with our code. Like:
main() { smart_ptr<Resource> res1(new Resource); smart_ptr<Resource> res2(res1); // Alternatively, don't initialize res2 and then assign res2 = res1; return 0; }
Resource destroyed Resource destroyed
  • In this case destructor of our Resource object will be called twice which can crash the program.
  • What if, instead of having our copy constructor and assignment operator copy the pointer (“copy semantics”), we instead transfer/move ownership of the pointer from the source to the destination object? This is the core idea behind move semantics. Move semantics means the class will transfer ownership of the object rather than making a copy.
  • Let’s update our smart_ptr class to show how this can be done:
<class T> class smart_ptr { T* m_ptr; public: smart_ptr(T* ptr=nullptr) :m_ptr(ptr) {} ~smart_ptr() { delete m_ptr; } // copy constructor that implements move semantics smart_ptr(smart_ptr& a) // note: not const { m_ptr = a.m_ptr; // transfer our dumb pointer from the source to our local object a.m_ptr = nullptr; // make sure the source no longer owns the pointer } // assignment operator that implements move semantics smart_ptr& operator=(smart_ptr& a) // note: not const { if (&a == this) return *this; delete m_ptr; // make sure we deallocate any pointer the destination is already holding first m_ptr = a.m_ptr; // then transfer our dumb pointer from the source to the local object a.m_ptr = nullptr; // make sure the source no longer owns the pointer return *this; } T& operator*() const { return *m_ptr; } T* operator->() const { return m_ptr; } }; class Resource { public: Resource() { std::cout << "Resource acquired\n"; } ~Resource() { std::cout << "Resource destroyed\n"; } }; int main() { smart_ptr<Resource> res1(new Resource); smart_ptr<Resource> res2(res1); return 0; }
Resource destroyed

std::auto_ptr , and why to avoid it #

  • What we have seen above as smart_ptr is basically an std::auto_ptr which was introduced in C++98, was C++’s first attempt at a standardized smart pointer.
  • However, std::auto_ptr (and our smart_ptr class) has a number of problems that make using it dangerous.
  • Because std::auto_ptr implements move semantics through the copy constructor and assignment operator, passing an std::auto_ptr by value to a function will cause your resource to get moved to the function parameter (and be destroyed at the end of the function when the function parameters go out of scope). Then when you go to access your std::auto_ptr argument from the caller (not realizing it was transferred and deleted), you’re suddenly dereferencing a null pointer. Crash!
  • std::auto_ptr always deletes its contents using non-array delete. This means std::auto_ptr won’t work correctly with dynamically allocated arrays, because it uses the wrong kind of deallocation. Worse, it won’t prevent you from passing it a dynamic array, which it will then mismanage, leading to memory leaks.
  • Because of the above-mentioned shortcomings, std::auto_ptr has been deprecated in C++11, and it should not used. In fact, std::auto_ptr slated for complete removal from the standard library as part of C++17!
  • Overriding the copy semantics to implement move semantics leads to weird edge cases and inadvertent bugs. Because of this, in C++11, the concept of “move” formally defined. And “move semantics” added to the language to properly differentiate copying from moving. In C++11, std::auto_ptr has been replaced by a bunch of other types of “move-aware” smart pointers: std::scoped_ptr , std::unique_ptr , std::weak_ptr , and std::shared_ptr .
  • We’ll also explore the two most popular of these: std::unique_ptr (which is a direct replacement for std::auto_ptr ) and std::shared_ptr .

std::unique_ptr with example in C++11 #

  • std::unique_ptr is the C++11 replacement for std::auto_ptr . It is used to manage use to manage any dynamically allocated object not shared by multiple objects. That is, std::unique_ptr should completely own the object it manages, not share that ownership with other classes.
  • We can convert our smart_ptr we designed above into std::unique_ptr . And for that one thing, we can do is delete the copy constructor & assignment operator so that no one can copy smart pointer.
  • As we are not allowing a copy of smart pointer we can’t pass our smart pointer to any function by value or return by value. And this is not good design.
  • To pass or return by value, we can add move constructor & move assignment operator, so that while passing or returning by value, we would have to transfer ownership through move semantics. This way we can also ensure single ownership throughout the lifetime of the object.
<class T> class smart_ptr { T* m_ptr; public: smart_ptr(T* ptr = nullptr) : m_ptr(ptr){} ~smart_ptr() { delete m_ptr; } // Copy constructor smart_ptr(const smart_ptr& a) = delete; // Move constructor smart_ptr(smart_ptr&& a) : m_ptr(a.m_ptr) { a.m_ptr = nullptr; } // Copy assignment smart_ptr& operator=(const smart_ptr& a) = delete; // Move assignment smart_ptr& operator=(smart_ptr&& a) { if (&a == this) return *this; delete m_ptr; m_ptr = a.m_ptr; a.m_ptr = nullptr; return *this; } T& operator*() const { return *m_ptr; } T* operator->() const { return m_ptr; } }; class Resource { public: Resource() { std::cout << "Resource acquired\n"; } ~Resource() { std::cout << "Resource destroyed\n"; } }; smart_ptr<Resource> func(smart_ptr<Resource> temp) { // Do something return temp; } int main() { smart_ptr<Resource> res1(new Resource); // smart_ptr<Resource> res3 = res1; // Won't compile, as copy contructor is deleted smart_ptr<Resource> res3 = func(std::move(res1)); // calls move semantics return 0; }
  • This is not the exact implementation of std::unique_ptr as there is deleter, implicit cast to bool & other security features included in an actual implementation, but this gives you a bigger picture of how std::unique_ptr is implemented.

References #

  • https://www.learncpp.com/cpp-tutorial/15-1-intro-to-smart-pointers-move-semantics/
  • https://stackoverflow.com/questions/106508/what-is-a-smart-pointer-and-when-should-i-use-one
  • https://docs.microsoft.com/en-us/cpp/cpp/smart-pointers-modern-cpp?view=vs-2017

std::unique_ptr

Defined in header <memory> .

Declarations ​

Description ​.

std::unique_ptr is a smart pointer that owns and manages another object through a pointer and disposes of that object when the unique_ptr goes out of scope.

The object is disposed of, using the associated deleter when either of the following happens:

the managing unique_ptr object is destroyed

the managing unique_ptr object is assigned another pointer via operator = or reset()

The object is disposed of, using a potentially user-supplied deleter by calling get_deleter()(ptr) . The default deleter uses the delete operator, which destroys the object and deallocates the memory.

A unique_ptr may alternatively own no object, in which case it is called empty .

There are two versions of std::unique_ptr :

  • Manages a single object (e.g. allocated with new );
  • Manages a dynamically-allocated array of objects (e.g. allocated with new[] ).

The class satisfies the requirements of MoveConstructible and MoveAssignable, but of neither CopyConstructible nor CopyAssignable.

Type requirements ​

Deleter must be FunctionObject or lvalue reference to a FunctionObject or lvalue reference to function, callable with an argument of type unique_ptr<T, Deleter>::pointer .

Only non-const unique_ptr can transfer the ownership of the managed object to another unique_ptr . If an object's lifetime is managed by a const std::unique_ptr , it is limited to the scope in which the pointer was created.

std::unique_ptr is commonly used to manage the lifetime of objects, including:

  • Providing exception safety to classes and functions that handle objects with dynamic lifetime, by guaranteeing deletion on both normal exit and exit through exception;
  • Passing ownership of uniquely-owned objects with dynamic lifetime into functions;
  • Acquiring ownership of uniquely-owned objects with dynamic lifetime from functions;
  • As the element type in move-aware containers, such as std::vector , which hold pointers to dynamically-allocated objects (e.g. if polymorphic behavior is desired).

std::unique_ptr may be constructed for an incomplete type T , such as to facilitate the use as a handle in the pImpl idiom. If the default deleter is used, T must be complete at the point in code where the deleter is invoked, which happens in the destructor, move assignment operator, and reset member function of std::unique_ptr . (Conversely, std::shared_ptr can't be constructed from a raw pointer to incomplete type, but can be destroyed where T is incomplete). Note that if T is a class template specialization, use of unique_ptr as an operand, e.g. !p requires T 's parameters to be complete due to ADL.

If T is a derived class of some base B , then std::unique_ptr<T> is implicitly convertible to std::unique_ptr<B> . The default deleter of the resulting std::unique_ptr<B> will use operator delete for B , leading to undefined behavior unless the destructor of B is virtual. Note that std::shared_ptr behaves differently: std::shared_ptr<B> will use the operator delete for the type T and the owned object will be deleted correctly even if the destructor of B is not virtual.

Unlike std::shared_ptr , std::unique_ptr may manage an object through any custom handle type that satisfies NullablePointer. This allows, for example, managing objects located in shared memory, by supplying a Deleter that defines typedef boost::offset_ptr pointer ; or another fancy pointer.

Feature-test macroValueStdComment
__cpp_lib_constexpr_memory202202L(C++23)constexpr std::unique_ptr

Member types ​

pubpointerstd::remove_reference<Deleter>::type::pointer if that type exists, otherwise T*. Must satisfy NullablePointer
pubelement_typeT, the type of the object managed by this unique_ptr
pubdeleter_typeDeleter, the function object or lvalue reference to function or to function object, to be called from the destructor

Member functions ​

pub constructs a new unique_ptr
pub destructs the managed object if such is present
pub assigns the unique_ptr

Modifiers ​

pub returns a pointer to the managed object and releases the ownership
pub replaces the managed object
pub swaps the managed objects

Observers ​

pub returns a pointer to the managed object
pub returns the deleter that is used for destruction of the managed object
pub checks if there is an associated managed object

Single-object version, unique_ptr<T> ​

pub dereferences pointer to the managed object

Array version, unique_ptr<T[]> ​

pub provides indexed access to the managed array

Non-member functions ​

pub
make_unique_for_overwrite
creates a unique pointer that manages a new object
pub
operator<
operator<=
operator>
operator>=
operator<=>
compares to another unique_ptr or with nullptr
pub outputs the value of the managed pointer to an output stream
pub specializes the std::swap algorithm

Helper Classes ​

pub hash support for std::unique_ptr
  • Declarations
  • Description
  • Member types
  • Member functions
  • Non-member functions
  • Helper Classes

Stack Exchange Network

Stack Exchange network consists of 183 Q&A communities including Stack Overflow , the largest, most trusted online community for developers to learn, share their knowledge, and build their careers.

Q&A for work

Connect and share knowledge within a single location that is structured and easy to search.

My implementation for std::unique_ptr

I just finished learning about move semantics and realized that a nice practical example for this concept is unique_ptr (it cannot be copied, only moved).

For learning purposes, and as a personal experiment, I proceed to try to create my implementation for a smart unique pointer:

For a small set of test cases, this is working like the real unique_ptr .

However, it just seems too simple enough.

I have two questions regarding this code:

  • Is it well-formed? i.e. does it follow common C++ standard and patterns (for example, should private members be declared before public ones?
  • Am I missing something regarding functionality? Is there maybe a bug in my code that I'm not seeing?
  • reinventing-the-wheel

Matias Cicero's user avatar

  • \$\begingroup\$ If there is something I can do to improve my question, feel free to comment any tips, don't just leave your downvote \$\endgroup\$ –  Matias Cicero Commented May 21, 2017 at 1:30
  • \$\begingroup\$ I left a downvote and an edit. Wasn't that enough information? \$\endgroup\$ –  πάντα ῥεῖ Commented May 21, 2017 at 1:50
  • 2 \$\begingroup\$ @πάνταῥεῖ You just added a missing tag. Do I deserve a downvote for that? \$\endgroup\$ –  Matias Cicero Commented May 21, 2017 at 2:18
  • \$\begingroup\$ Do you really need to reinvent the square wheel? Can you elaborate bout why actually? \$\endgroup\$ –  πάντα ῥεῖ Commented May 21, 2017 at 3:04
  • 1 \$\begingroup\$ Did you mean to omit the members that allow you to actually use a unique pointer? I mean, operator*() and operator->() . \$\endgroup\$ –  Toby Speight Commented May 22, 2017 at 11:06

2 Answers 2

Is it well-formed?

It compiles, so yes.

i.e. does it follow common C++ standard and patterns (for example, should private members be declared before public ones?

Personally I think so.

When reading the code I want to know the members so I can verify that the constructors initialize them all, as a result I usually put them first. But other people prefer to put all private stuff at the bottom.

Am I missing something regarding functionality?

Yes. Quite a lot.

Is there maybe a bug in my code that I'm not seeing?

Yes. It potentially leaks on assignment.

Code Review

Constructing from object.

That's exceedingly dangerous:

Use member initializing list.

You should always attempt to use the member initializer list for initializing members. Any non-trivial object will have its constructor called before the initializer code is called and thus it is inefficient to then re-initialize it in the code.

Member variable Names

Prefer not to use _ as the first character in an identifier name.

Even if you know all the rules of when to use them most people don't so they are best avoided. If you must have a prefix to identify members use m_ - but if you name your member variables well then there is no need for any prefix (in my opinion prefixes makes the code worse not better, because you are relying on unwritten rules. If you have good well-defined names (see self-documenting code) then members should be obvious).

The move operators should be marked as noexcept .

When used with standard containers this will enable certain optimizations. This is because if the move is noexcept then certain operations can be guaranteed to work and thus provide the strong exception guarantee.

Leak in assignment

Note: Your current assignment potentially leaks. If this currently has a pointer assigned then you overwrite it without freeing.

Checking for this pessimization

Yes you do need to make it work when there is self assignment. But in real code the self assignment happens so infrequently that this test becomes a pessimization on the normal case (same applies for copy operation). There have been studies on this (please somebody post a link; I have lost mine and would like to add it back to my notes).

The standard way of implementing move is via swap. Just like Copy is normally implemented by Copy and Swap.

Using the swap technique also delays the calling of the destructor on the pointer for the current object. Which means that it can potentially be re-used. But if it is going out of scope the unique_ptr destructor will correctly destroy it.

Good first try but still lots of issues.

Please read the article I wrote on unique_ptr and shared_ptr for lots more things you should implement.

Smart-Pointer - Unique Pointer Smart-Pointer - Shared Pointer Smart-Pointer - Constructors

Some things you missed:

  • Constructor with nullptr
  • Constructor from derived type
  • Casting to bool
  • Checking for empty
  • Guaranteeing delete on construction failure.
  • Implicit construction issues
  • Dereferencing

When you have read all three articles then the bare bones unique_ptr looks like this:

Test to make sure it compiles:

Loki Astari's user avatar

  • \$\begingroup\$ What would be a safer way of constructing the unique_ptr from a pointer of type T? \$\endgroup\$ –  dav Commented Jul 20, 2018 at 23:18
  • \$\begingroup\$ @DavidTran. Please look at the standard version and its interface. \$\endgroup\$ –  Loki Astari Commented Jul 22, 2018 at 6:13
  • \$\begingroup\$ @Mashpoe there is no need to check if a pointer is null before calling delete. \$\endgroup\$ –  Loki Astari Commented Jan 14, 2019 at 17:02
  • \$\begingroup\$ @U62 Compiles fine for me. In both cases they are converted to the correct type before the swap. It will only fail to compile if the class U is not derived from the class T which is exactly what it is supposed to do . \$\endgroup\$ –  Loki Astari Commented Apr 5, 2019 at 16:51
  • 1 \$\begingroup\$ @user4893106 much of that constructor ridiculousness... : For an average class zero. In most situations the default implementation works out of the box with no need to do anything. For complex classes like this case there is usually a standard implementation already available in std:: . Not sure what "simple ops only" means. \$\endgroup\$ –  Loki Astari Commented Sep 3, 2020 at 18:06

Yes, have good formatting

I have the same thought present in Martin York' answer:

Yes, you forgot to add T, and T[], and the following features:

type* release();

void reset(type* item);

void swap(unique_ptr &other);

type* get();

operator->;

operator[];

Yes, you must force the receiving of types strictly to be pointers

Copy assignment operator

This is redundant, this part is not necessary as this operator will never be called taking into account that the motion constructor exists and the copy constructor is disabled (= delete).

Template only typename T

You must accept both types T, and T[], ie: array or not.

Constructing from object

Verify in move assignment operator.

Before _ptr =, you need to check if this->ptr is initialized, if yes delete ptr before assign.

This above code is incorrect, this is pointer and uptr is reference, you need to add &other to verify successfully

Note: std::move in uptr._ptr is irrelevant.

Example code

Lucas Paixão's user avatar

  • \$\begingroup\$ I certainly didn't plagiarize the answer, I adopted the same html design pattern to create my answer, but the content is different, obviously I forgot to put the proper reference to the two contents I mentioned the previous answer, being them #NoExcept and #It follow common C++, as my way of thinking is similar. Anyway, in these specific topics I added the reference to the original answer (@Martin York), thanks for the warning. \$\endgroup\$ –  Lucas Paixão Commented Sep 22, 2021 at 19:02

Your Answer

Sign up or log in, post as a guest.

Required, but never shown

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy .

Not the answer you're looking for? Browse other questions tagged c++ c++11 reinventing-the-wheel pointers or ask your own question .

  • Featured on Meta
  • Bringing clarity to status tag usage on meta sites
  • We've made changes to our Terms of Service & Privacy Policy - July 2024
  • Announcing a change to the data-dump process

Hot Network Questions

  • John 1:1, "the Word was with God, and the Word was God." Vs2, He was in the beginning with God. Does this not prove Jesus existed before Genesis 1:1?
  • Can I travel with regional trains from operators other than DB if I can "use any train" due to a schedule change?
  • What to do if sample size obtained is much larger than indicated in the power analysis?
  • What can cause a 24 volt solar panel to output 40 volt?
  • Genus 0 curves on surfaces and the abc conjecture
  • How to read data from Philips P2000C over its serial port to a modern computer?
  • Minimum number of oracle call to solve Simon problem by a (NDTM) non-deterministic Turing machine?
  • 1 amen for 2 berachot?
  • How do you "stealth" a relativistic superweapon?
  • Why is deontological ethics the opposite of teleological ethics and not "ontological" ethics
  • Why do these finite group Dedekind matrices seem to have integer spectrum when specialized to the order of group elements?
  • Do temperature variations make trains on Mars impractical?
  • Does H3PO exist?
  • What's the airplane with the smallest ratio of wingspan to fuselage width?
  • What is the number ways to count tuples whose sum is zero?
  • Making a bracha mentally in case of doubt
  • Guitar amplifier placement for live band
  • Why did R Yochanan say 'We' when he Refuted Reish Lakish on his own?
  • Finding a Linear Algebra reading topic
  • Where will the ants position themselves so that they are precisely twice as far from vinegar as they are from peanut butter?
  • UART pin acting as power pin
  • Elements of finite order in the group of invertible affine transformations
  • Specify geo location of web pages (each is different)
  • Norm in the minimal tensor product of C*-algebras

unique_ptr c assignment

cppreference.com

Std::unique_ptr<t,deleter>:: operator=.

(C++20)
(C++20)
(C++11)
(C++20)
(C++17)
(C++11)
(C++11)
(basic types, RTTI)
(C++20)
(C++20)
three_way_comparable_with (C++20)
   
is_ltis_lteq (C++20)(C++20)
is_gtis_gteq (C++20)(C++20)
General utilities
(C++20)
(deprecated in C++20)
rel_ops::operator>
rel_ops::operator>=
cmp_lesscmp_less_than (C++20)(C++20)   
cmp_greatercmp_greater_than (C++20)(C++20)


  
  
(until C++23)
(until C++23)
(until C++23)
(until C++23)
(until C++23)
(until C++23)



)
)
)
start_lifetime_as_array (C++23)

)

unique_ptr::operator->
make_unique_for_overwrite (C++20)
operator!=operator<operator>operator<=operator>=operator<=> (until C++20)(C++20)
operator=( unique_ptr&& r ) noexcept; (1) (constexpr since C++23)
< class U, class E >
unique_ptr& operator=( unique_ptr<U, E>&& r ) noexcept;
(2) (constexpr since C++23)
operator=( ) noexcept; (3) (constexpr since C++23)
operator=( const unique_ptr& ) = delete; (4)
  • Deleter is not MoveAssignable , or
  • assigning get_deleter() from an rvalue of type Deleter would throw an exception.
  • std::remove_reference<Deleter>::type is not CopyAssignable , or
  • assigning get_deleter() from an lvalue of type Deleter would throw an exception.
  • U is not an array type,
  • unique_ptr<U, E>::pointer is implicitly convertible to pointer , and
  • std:: is_assignable < Deleter & , E && > :: value is true .
  • U is an array type,
  • pointer is the same type as element_type* ,
  • unique_ptr<U, E>::pointer is the same type as unique_ptr<U, E>::element_type* ,
  • unique_ptr<U, E>::element_type(*)[] is convertible to element_type(*)[] , and
Parameters Return value Notes Example Defect reports

[ edit ] Parameters

r - smart pointer from which ownership will be transferred

[ edit ] Return value

[ edit ] notes.

As a move-only type, unique_ptr 's assignment operator only accepts rvalues arguments (e.g. the result of std::make_unique or a std::move 'd unique_ptr variable).

[ edit ] Example

[ edit ] defect reports.

The following behavior-changing defect reports were applied retroactively to previously published C++ standards.

DR Applied to Behavior as published Correct behavior
C++11 for overload (2), was assigned from
<Deleter>(r.get_deleter())
corrected to
<E>(r.get_deleter())
C++11
rejected qualification conversions
accepts
C++11 the converting assignment operator was not constrained constrained
C++11 the move assignment operator was not constrained constrained
  • Recent changes
  • Offline version
  • What links here
  • Related changes
  • Upload file
  • Special pages
  • Printable version
  • Permanent link
  • Page information
  • In other languages
  • This page was last modified on 6 October 2023, at 13:15.
  • Privacy policy
  • About cppreference.com
  • Disclaimers

Powered by MediaWiki

  • C++ Data Types
  • C++ Input/Output
  • C++ Pointers
  • C++ Interview Questions
  • C++ Programs
  • C++ Cheatsheet
  • C++ Projects
  • C++ Exception Handling
  • C++ Memory Management

Unique_ptr in C++

std::unique_ptr is a smart pointer introduced in C++11. It automatically manages the dynamically allocated resources on the heap. Smart pointers are just wrappers around regular old pointers that help you prevent widespread bugs. Namely, forgetting to delete a pointer and causing a memory leak or accidentally deleting a pointer twice or in the wrong way. They can be used in a similar way to standard pointers. They automate some of the manual processes that cause common bugs.

Prerequisites: Pointer in C++ , Smart Pointers in C++.

  • unique_ptr<A>: It specifies the type of the std::unique_ptr. In this case- an object of type A.
  • new A : An object of type A is dynamically allocated on the heap using the new operator.
  • ptr1 : This is the name of the std::unique_ptr variable.

What happens when unique_ptr is used?

When we write unique_ptr<A> ptr1 (new A), memory is allocated on the heap for an instance of datatype A. ptr1 is initialized and points to newly created A object. Here, ptr1 is the only owner of the newly created object A and it manages this object’s lifetime. This means that when ptr1 is reset or goes out of scope, memory is automatically deallocated and A’s object is destroyed.

When to use unique_ptr?

When ownership of resource is required. When we want single or exclusive ownership of a resource, then we should go for unique pointers. Only one unique pointer can point to one resource. So, one unique pointer cannot be copied to another. Also, it facilitates automatic cleanup when dynamically allocated objects go out of scope and helps preventing memory leaks.

Note: We need to use the <memory> header file for using these smart pointers.

Examples of Unique_ptr

Lets create a structure A and it will have a method named printA to display some text. Then in the main section, let’s create a unique pointer that will point to the structure A. So at this point, we have an instance of structure A and p1 holds the pointer to that.

     

Now let’s create another pointer p2 and we will try to copy the pointer p1 using the assignment operator(=).

     

The above code will give compile time error as we cannot assign pointer p2 to p1 in case of unique pointers. We have to use the move semantics for such purpose as shown below.

Managing object of type A using move semantics.

       

Note once the address in pointer p1 is copied to pointer p2, the pointer p1’s address becomes NULL(0) and the address stored by p2 is now the same as the address stored by p1 showing that the address in p1 has been transferred to the pointer p2 using the move semantics.

Please Login to comment...

Similar reads.

  • Geeks Premier League
  • Geeks Premier League 2023

Improve your Coding Skills with Practice

 alt=

What kind of Experience do you want to share?

thisPointer

Programming Tutorials

  • Reset unique_ptr in Modern C++

When working with unique_ptr in C++, it’s essential to know how to renounce the ownership of the managed object and free the associated memory when necessary. The unique_ptr class provides the reset() member function for this purpose.

The unique_ptr::reset() Function

Calling the reset() method on a unique_ptr will perform two operations:

  • It will deallocate or release the memory that the unique_ptr currently owns.
  • It will set the unique_ptr itself to point to nullptr , effectively indicating that it no longer manages any memory.

Example of reset() function of unique_ptr

Let’s explore how this works with an example using an int as the managed object for simplicity:

Check if a unique_ptr object is NULL

After you have called reset() , it’s a good practice to check whether the unique_ptr is indeed empty (i.e., it now points to nullptr ). You can do this by directly using the unique_ptr in a condition as it has an operator bool defined which checks for ownership of an object:

Why Reset a unique_ptr ?

Resetting a unique_ptr can be useful in several scenarios:

Frequently Asked:

  • How to use unique_ptr with Arrays in C++?
  • Copying and Moving unique_ptr in C++
  • How to Return unique_ptr from a function in C++?
  • When you want to safely release the resource before the unique_ptr goes out of scope.
  • If you need to reuse the unique_ptr for a new resource.
  • To ensure that the unique_ptr does not maintain a dangling pointer to a resource that has been managed elsewhere.

The ability to reset a unique_ptr is an integral part of its functionality, providing you with control over when to free the managed memory. It also helps in preventing memory leaks by ensuring that memory is not inadvertently retained. WRemember, once reset, always check the unique_ptr before using it to avoid accessing nullptr .

Related posts:

  • What is shared_ptr in C++?
  • Shared_ptr & Custom Deleter in Modern C++
  • Smart Pointer vs Raw Pointer in C++
  • How not to use Smart Pointers in C++?
  • What is weak_ptr in Modern C++ & why do we need it?
  • What is unique_ptr in C++?
  • Introduction to Smart Pointers in Modern C++
  • Using std::find & std::find_if with User Defined Classes
  • C++11 Multithreading – Part 4: Data Sharing and Race Conditions
  • C++11 Multithreading – Part 5: Using mutex to fix Race Conditions
  • C++ Set example and Tutorial – Part 1
  • C++11 Multithreading – Part 7: Condition Variables Explained
  • C++11 Multithreading – Part 8: std::future , std::promise and Returning values from Thread
  • Lambda Functions in C++
  • std::bind in C++ – Explained with Examples
  • The auto Keyword in C++11
  • multimap Example and Tutorial in C++
  • C++11 Multithreading – Part 9: std::async Tutorial & Example
  • How to Capture Member Variables in Lambda function in C++?

Share your love

Leave a comment cancel reply.

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed .

  • Stack Overflow for Teams Where developers & technologists share private knowledge with coworkers
  • Advertising & Talent Reach devs & technologists worldwide about your product, service or employer brand
  • OverflowAI GenAI features for Teams
  • OverflowAPI Train & fine-tune LLMs
  • Labs The future of collective knowledge sharing
  • About the company Visit the blog

Collectives™ on Stack Overflow

Find centralized, trusted content and collaborate around the technologies you use most.

Q&A for work

Connect and share knowledge within a single location that is structured and easy to search.

Get early access and see previews of new features.

c++ move/copy/assignment with a unique_ptr<AbstractClass> member variable

I have a problem very similar to

How to make a class with a member of unique_ptr work with std::move and std::swap?

and I am using VS2013 so I expect the following to work.

path\engine.cpp(75): error C2280: 'std::unique_ptr> &std::unique_ptr<_Ty,std::default_delete<_Ty>>::operator =(const std::unique_ptr<_Ty,std::default_delete<_Ty>> &)' : attempting to reference a deleted function with [ _Ty=AbstractCamera ] other_path\memory(1487) : see declaration of 'std::unique_ptr>::operator =' with [ _Ty=AbstractCamera ] This diagnostic occurred in the compiler generated function 'RenderManager &RenderManager::operator =(const RenderManager &)'

I do get that simple examples like

are not allowed but my problem is the following code:

because the assignment operator of unique_ptr is deleted but how does this affect a class hierarchy like those of Engine->RenderManger->unique_ptr member.

I do get, that Engine e uses the default constructor Engine() and e = Engine() calls the default constructor and the operator= of Engine to assign the temporary Engine object to e.

My question therefore is: where does the code try to copy/assign unique_ptr and how do I resolve it?

I tried to strip the original code down as much as possible but was not able to reproduce the error using a simpler example and ideone in form of a SSCCEE as I do not really understand what causes the problem, so sorry for that!

Community's user avatar

  • Yes. Sorry, this is one of the typos from the minimization of the original code as pointed out by T.C. Thank you for pointing this typo out, so I could correct it, s.t. the original question contains one error less! –  Kevin Streicher Commented Feb 20, 2015 at 19:31

3 Answers 3

VS2013 does not automatically generate move special member functions (this is non-conforming, in case it isn't obvious). You'll have to write the move constructor and move assignment operator of Engine and RenderManager yourself, as otherwise the copy special member functions will be used.

As a side note, _currentCamera(std::move(std::make_unique<CameraImpl>)) won't compile; _currentCamera(std::move(std::make_unique<CameraImpl>())) would but the std::move is useless and a pessimization. make_unique already returns an rvalue. There are also several other typos in your code, presumably caused by the minimization process.

T.C.'s user avatar

  • Thank you very much and yes, sadly you are right there are typos because of the minimization. I will try to correct them in the original post for people who read this later. I will try this now! Thank you for the fast response! Could explain what you mean with: and a pessimization , simply "uncessary"? –  Kevin Streicher Commented Feb 20, 2015 at 19:28
  • 1 @NoxMortem It inhibits copy elision. –  T.C. Commented Feb 20, 2015 at 19:41
  • oh, ouch. Thank you very much for pointing that out, this is some small but important information. –  Kevin Streicher Commented Feb 20, 2015 at 19:53

T.C. correctly answered the question, but I wanted to give some further insights as I did actually asked the wrong question :)

The real question therefore should have been

How can I use the following code
when my intent is the destruction of the default constructed object e and the assignment of the newly constructed object.

First of all one needs to understand the difference between copy and move assignment and construction and the following thread and especially the two long posts by @FredOverflow here can help very much to understand this: What are move semantics?

The problem setting are actually classes with std::vectors<std::unique_ptr<T>> and classes with std::unique_ptr<T> members. See http://www.cplusplus.com/forum/beginner/110610/ and the answer of JLJorges for a longer example.

JLJorges posted:

So don't do anything: by default B is not Copyable or Assignable, but B is Moveable and MoveAssignable

JLJorges pointed out two important things under such circumstances:

  • A class containing a non-copyable member can not be copyable by default.
  • A class containing a non-copyable but moveable/moveAssignable member can still be moveable/moveAssigneable by default.

VS2013 therefore is able to implicitly generate move and move assign operators/constructors as it does exactly this for such a class setup.

The reason I did not select T.C.'s answer altough he was very helpful and close to the answer is the following:

In case one needs copy-able/copy-assignable classes he has to implement copy-constructor and copy-assignment . This would have been the answer if I would have needed exactly what the code in the initial question looked like: a copy/copy-assignable class Engine.

In case one implements one of those methods/operators he might want to implement the others as well, see the following links for explanations:

  • Rule-of-Three becomes Rule-of-Five with C++11?
  • http://en.wikipedia.org/wiki/Rule_of_three_%28C%2B%2B_programming%29#Rule_of_5

As I said, I had the asked the wrong question, as I did not needed a copyable/copyassignable class the solution would have been to implement move constructor and move assign operator or like JLJorges pointed out: do nothing and use the implicitly generated version, but when I wanted to move I obviously had to tell the compiler this:

e = Engine() calls Engine's move assignment operator. Since you don't have one, it's copy assignment operator will be called. Then RenderManger's copy assignment will be called. Finally it's the copy assignment of unique_ptr, which is deleted.

A move assignment is needed for Engine, as

Engine & operator = (Engine && rhs) { r._currentCamera = std::move(rhs.r._currentCamera); return * this; }

Suppose RenderManager::_currentCamera is visible to Engine, otherwise you need to defind move assignment for RenderManager.

imlyc's user avatar

Your Answer

Reminder: Answers generated by artificial intelligence tools are not allowed on Stack Overflow. Learn more

Sign up or log in

Post as a guest.

Required, but never shown

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy .

Not the answer you're looking for? Browse other questions tagged c++ c++11 or ask your own question .

  • Featured on Meta
  • We've made changes to our Terms of Service & Privacy Policy - July 2024
  • Bringing clarity to status tag usage on meta sites
  • Feedback requested: How do you use tag hover descriptions for curating and do...

Hot Network Questions

  • Do temperature variations make trains on Mars impractical?
  • are "lie low" and "keep a low profile" interchangeable?
  • Unexpected behaviour during implicit conversion in C
  • Phrase for giving up?
  • Is there a source for there being a Psalm inscribed on King David's shield?
  • Creating a deadly "minimum altitude limit" in an airship setting
  • Harmonic, partial, overtone. Which is which?
  • Does a Way of the Astral Self Monk HAVE to do force damage with Arms of the Astral Self from 10' away, or can it be bludgeoning?
  • Minimum number of oracle call to solve Simon problem by a (NDTM) non-deterministic Turing machine?
  • Making a bracha mentally in case of doubt
  • How predictable are the voting records of members of the US legislative branch?
  • John 1:1, "the Word was with God, and the Word was God." Vs2, He was in the beginning with God. Does this not prove Jesus existed before Genesis 1:1?
  • Why is deontological ethics the opposite of teleological ethics and not "ontological" ethics
  • Can I travel with regional trains from operators other than DB if I can "use any train" due to a schedule change?
  • Function to find the most common numeric ordered pairings (value, count)
  • What is the good errorformat or compiler plugin for pyright?
  • Why did R Yochanan say 'We' when he Refuted Reish Lakish on his own?
  • How would a culture living in an extremely vertical environment deal with dead bodies?
  • Finding a Linear Algebra reading topic
  • If I purchase a house through an installment sale, can I use it as collateral for a loan?
  • Why do these finite group Dedekind matrices seem to have integer spectrum when specialized to the order of group elements?
  • How do you "stealth" a relativistic superweapon?
  • A man hires someone to murders his wife, but she kills the attacker in self-defense. What crime has the husband committed?
  • What's the sales pitch for waxing chains?

unique_ptr c assignment

IMAGES

  1. Smart Pointers in C++ and How to Use Them

    unique_ptr c assignment

  2. How to create and use unique pointer in C++?

    unique_ptr c assignment

  3. Unique_ptr in C++

    unique_ptr c assignment

  4. What is the C++ unique_ptr?

    unique_ptr c assignment

  5. How to create and use unique pointer in C++?

    unique_ptr c assignment

  6. C++ How-To Series : Smart / unique std::unique_ptr and raw pointers

    unique_ptr c assignment

COMMENTS

  1. std::unique_ptr

    std::unique_ptr is a smart pointer that owns and manages another object through a pointer and disposes of that object when the unique_ptr goes out of scope.. The object is disposed of, using the associated deleter when either of the following happens: the managing unique_ptr object is destroyed.; the managing unique_ptr object is assigned another pointer via operator= or reset().

  2. How to assign value to the unique_ptr after declaring it?

    0. In order to assign a new value to a std::unique_ptr use the reset() method. However, a big word of caution regarding the use of this method is that the std::unique_ptr object will try to dispose of the managed pointer by invoking a Deleter function on the managed pointer when the std::unique_ptr object will be being destroyed or when the ...

  3. unique_ptr

    a stored deleter: a callable object that takes an argument of the same type as the stored pointer and is called to delete the managed object. It is set on construction, can be altered by an assignment operation, and can be individually accessed using member get_deleter. unique_ptr objects replicate a limited pointer functionality by providing ...

  4. std::unique_ptr<T,Deleter>::unique_ptr

    unique_ptr(const unique_ptr&)= delete; (7) 1) Constructs a std::unique_ptr that owns nothing. Value-initializes the stored pointer and the stored deleter. Requires that Deleter is DefaultConstructible and that construction does not throw an exception. These overloads participate in overload resolution only if std::is_default_constructible ...

  5. unique_ptr

    Constructs a unique_ptr object, depending on the signature used: default constructor (1), and (2) The object is empty (owns nothing), with value-initialized stored pointer and stored deleter. construct from pointer (3) The object takes ownership of p, initializing its stored pointer to p and value-initializing its stored deleter. construct from pointer + lvalue deleter (4)

  6. 22.5

    std::unique_ptr is by far the most used smart pointer class, so we'll cover that one first. In the following lessons, we'll cover std::shared_ptr and std::weak_ptr. std::unique_ptr. std::unique_ptr is the C++11 replacement for std::auto_ptr. It should be used to manage any dynamically allocated object that is not shared by multiple objects.

  7. std::unique_ptr<T,Deleter>::reset

    Return value (none) [] NoteTo replace the managed object while supplying a new deleter as well, move assignment operator may be used. A test for self-reset, i.e. whether ptr points to an object already managed by * this, is not performed, except where provided as a compiler extension or as a debugging assert.Note that code such as p. reset (p. release ()) does not involve self-reset, only code ...

  8. unique_ptr

    The assignment operation between unique_ptr objects that point to different types (3) needs to be between types whose pointers are implicitly convertible, and shall not involve arrays in any case (the third signature is not part of the array specialization of unique_ptr). Copy assignment (4) to a unique_ptr type is not allowed (deleted signature).

  9. How to: Create and use unique_ptr instances

    In this article. 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. This means that the ownership of the memory resource is transferred to another unique_ptr and the original unique_ptr no longer owns it.

  10. Understanding unique_ptr with Example in C++11

    std::auto_ptr, and why to avoid it#. What we have seen above as smart_ptr is basically an std::auto_ptr which was introduced in C++98, was C++'s first attempt at a standardized smart pointer.; However, std::auto_ptr (and our smart_ptr class) has a number of problems that make using it dangerous. Because std::auto_ptr implements move semantics through the copy constructor and assignment ...

  11. std::unique_ptr

    Description. std::unique_ptr is a smart pointer that owns and manages another object through a pointer and disposes of that object when the unique_ptr goes out of scope. The object is disposed of, using the associated deleter when either of the following happens: The object is disposed of, using a potentially user-supplied deleter by calling ...

  12. My implementation for std::unique_ptr

    Copy assignment operator unique_ptr<T>& operator=(const unique_ptr<T>& uptr) = delete; This is redundant, this part is not necessary as this operator will never be called taking into account that the motion constructor exists and the copy constructor is disabled (= delete).

  13. std::unique_ptr<T,Deleter>::operator=

    For the array specialization (unique_ptr<T[]>), this overload participates in overload resolution only if U is an array type, ... As a move-only type, unique_ptr's assignment operator only accepts rvalues arguments (e.g. the result of std::make_unique or a std::move 'd unique_ptr variable).

  14. Unique_ptr in C++

    std::unique_ptr is a smart pointer introduced in C++11. It automatically manages the dynamically allocated resources on the heap. Smart pointers are just wrappers around regular old pointers that help you prevent widespread bugs. Namely, forgetting to delete a pointer and causing a memory leak or accidentally deleting a pointer twice or in the ...

  15. What is unique_ptr in C++?

    A unique_ptr is a type of smart pointer provided by the C++ Standard Library that is designed to manage the memory of a dynamically allocated memory. It holds the exclusive ownership of the memory it points to, meaning there can be no other unique_ptr pointing to the same memory at the same time. This exclusive ownership is the first way in ...

  16. Proper way to create unique_ptr that holds an allocated array

    The 2 statements are not equivalent. The second one value initializes the array, while the first one creates the array uninitialized. In that sense make_unique isn't always better than constructor plus new.That means for use-cases where value-initialization isn't needed and to be avoided because it is performance critical the constructor version is better.

  17. Copying and Moving unique_ptr in C++

    In C++, a unique_ptr is a smart pointer that owns and manages dynamically allocated memory. It automatically deletes the linked memory when the unique_ptr goes out of scope. One key aspect of unique_ptr is ownership uniqueness, meaning that there can only be one unique_ptr pointing to any given resource at a time. This uniqueness is enforced by the language to prevent multiple unique_ptrs from ...

  18. Reset unique_ptr in Modern C++

    When working with unique_ptr in C++, it's essential to know how to renounce the ownership of the managed object and free the associated memory when necessary. The unique_ptr class provides the reset() member function for this purpose.. The unique_ptr::reset() Function. Calling the reset() method on a unique_ptr will perform two operations:. It will deallocate or release the memory that the ...

  19. Copy constructor for a class with unique_ptr

    The usual case for one to have a unique_ptr in a class is to be able to use inheritance (otherwise a plain object would often do as well, see RAII). For this case, there is no appropriate answer in this thread up to now. So, here is the starting point: struct Base { //some stuff }; struct Derived : public Base { //some stuff }; struct Foo { std::unique_ptr<Base> ptr; //points to Derived or ...

  20. c++11

    e = Engine() calls Engine's move assignment operator. Since you don't have one, it's copy assignment operator will be called. Then RenderManger's copy assignment will be called. Finally it's the copy assignment of unique_ptr, which is deleted. A move assignment is needed for Engine, as. Engine & operator = (Engine && rhs) {.