[
Note: The uses
of
unique_ptr include providing exception safety for
dynamically allocated memory, passing ownership of dynamically allocated
memory to a function, and returning dynamically allocated memory from a
function
. —
end note ]
namespace std {
template<class T> struct default_delete;
template<class T> struct default_delete<T[]>;
template<class T, class D = default_delete<T>> class unique_ptr;
template<class T, class D> class unique_ptr<T[], D>;
template<class T, class... Args> unique_ptr<T> make_unique(Args&&... args);
template<class T> unique_ptr<T> make_unique(size_t n);
template<class T, class... Args> unspecified make_unique(Args&&...) = delete;
template<class T, class D> void swap(unique_ptr<T, D>& x, unique_ptr<T, D>& y) noexcept;
template<class T1, class D1, class T2, class D2>
bool operator==(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template<class T1, class D1, class T2, class D2>
bool operator!=(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template<class T1, class D1, class T2, class D2>
bool operator<(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template<class T1, class D1, class T2, class D2>
bool operator<=(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template<class T1, class D1, class T2, class D2>
bool operator>(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template<class T1, class D1, class T2, class D2>
bool operator>=(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template <class T, class D>
bool operator==(const unique_ptr<T, D>& x, nullptr_t) noexcept;
template <class T, class D>
bool operator==(nullptr_t, const unique_ptr<T, D>& y) noexcept;
template <class T, class D>
bool operator!=(const unique_ptr<T, D>& x, nullptr_t) noexcept;
template <class T, class D>
bool operator!=(nullptr_t, const unique_ptr<T, D>& y) noexcept;
template <class T, class D>
bool operator<(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator<(nullptr_t, const unique_ptr<T, D>& y);
template <class T, class D>
bool operator<=(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator<=(nullptr_t, const unique_ptr<T, D>& y);
template <class T, class D>
bool operator>(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator>(nullptr_t, const unique_ptr<T, D>& y);
template <class T, class D>
bool operator>=(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator>=(nullptr_t, const unique_ptr<T, D>& y);
}
namespace std {
template <class T, class D = default_delete<T>> class unique_ptr {
public:
using pointer = see below;
using element_type = T;
using deleter_type = D;
constexpr unique_ptr() noexcept;
explicit unique_ptr(pointer p) noexcept;
unique_ptr(pointer p, see below d1) noexcept;
unique_ptr(pointer p, see below d2) noexcept;
unique_ptr(unique_ptr&& u) noexcept;
constexpr unique_ptr(nullptr_t) noexcept;
template <class U, class E>
unique_ptr(unique_ptr<U, E>&& u) noexcept;
~unique_ptr();
unique_ptr& operator=(unique_ptr&& u) noexcept;
template <class U, class E> unique_ptr& operator=(unique_ptr<U, E>&& u) noexcept;
unique_ptr& operator=(nullptr_t) noexcept;
add_lvalue_reference_t<T> operator*() const;
pointer operator->() const noexcept;
pointer get() const noexcept;
deleter_type& get_deleter() noexcept;
const deleter_type& get_deleter() const noexcept;
explicit operator bool() const noexcept;
pointer release() noexcept;
void reset(pointer p = pointer()) noexcept;
void swap(unique_ptr& u) noexcept;
unique_ptr(const unique_ptr&) = delete;
unique_ptr& operator=(const unique_ptr&) = delete;
};
}
The default type for the template parameter
D is
default_delete. A client-supplied template argument
D shall be a function
object type (
[function.objects]), lvalue reference to function, or
lvalue reference to function object type
for which, given
a value
d of type
D and a value
ptr of type
unique_ptr<T, D>::pointer, the expression
d(ptr) is valid and has the effect of disposing of the
pointer as appropriate for that deleter
.If the deleter's type
D is not a reference type,
D shall satisfy
the requirements of
Destructible (Table
27)
.If the
qualified-id remove_reference_t<D>::pointer is valid and denotes a
type (
[temp.deduct]), then
unique_ptr<T,
D>::pointer shall be a synonym for
remove_reference_t<D>::pointer. Otherwise
unique_ptr<T, D>::pointer shall be a synonym for
element_type*. [
Example: Given an allocator type
X (
[allocator.requirements]) and
letting
A be a synonym for
allocator_traits<X>, the types
A::pointer,
A::const_pointer,
A::void_pointer, and
A::const_void_pointer
may be used as
unique_ptr<T, D>::pointer. —
end example ]
constexpr unique_ptr() noexcept;
constexpr unique_ptr(nullptr_t) noexcept;
Requires: D shall
satisfy the requirements of
DefaultConstructible (Table
22),
and that construction shall not throw an exception
. Effects: Constructs a
unique_ptr object that owns
nothing, value-initializing the stored pointer and the stored deleter
. Postconditions: get() == nullptr. get_deleter()
returns a reference to the stored deleter
. Remarks: If
is_pointer_v<deleter_type> is
true or
is_default_constructible_v<deleter_type> is
false,
this constructor shall not participate in overload resolution
. explicit unique_ptr(pointer p) noexcept;
Requires: D shall
satisfy the requirements of
DefaultConstructible (Table
22),
and that construction shall not throw an exception
. Effects: Constructs a
unique_ptr which owns
p, initializing the stored pointer with
p and
value-initializing the stored deleter
. Postconditions: get() == p. get_deleter()
returns a reference to the stored deleter
. Remarks: If
is_pointer_v<deleter_type> is
true or
is_default_constructible_v<deleter_type> is
false,
this constructor shall not participate in overload resolution
. If class template argument deduction (
[over.match.class.deduct])
would select the function template corresponding to this constructor,
then the program is ill-formed
.unique_ptr(pointer p, see below d1) noexcept;
unique_ptr(pointer p, see below d2) noexcept;
The signature of these constructors depends upon whether
D
is a reference type
. If D is a non-reference type
A, then the signatures are:
unique_ptr(pointer p, const A& d) noexcept;
unique_ptr(pointer p, A&& d) noexcept;
If D is an lvalue reference type A&,
then the signatures are:
unique_ptr(pointer p, A& d) noexcept;
unique_ptr(pointer p, A&& d) = delete;
If D is an lvalue reference type const A&,
then the signatures are:
unique_ptr(pointer p, const A& d) noexcept;
unique_ptr(pointer p, const A&& d) = delete;
Effects: Constructs a
unique_ptr object which owns
p, initializing
the stored pointer with
p and initializing the deleter
from
std::forward<decltype(d)>(d). Remarks: These constructors shall not participate in overload resolution
unless
is_constructible_v<D, decltype(d)> is
true. Postconditions: get() == p. get_deleter() returns a reference to the stored
deleter
. If
D is a reference type then
get_deleter()
returns a reference to the lvalue
d.Remarks: If class template argument deduction (
[over.match.class.deduct])
would select a function template corresponding to either of these constructors,
then the program is ill-formed
. [
Example:
D d;
unique_ptr<int, D> p1(new int, D()); unique_ptr<int, D> p2(new int, d); unique_ptr<int, D&> p3(new int, d); unique_ptr<int, const D&> p4(new int, D());
—
end example ]
unique_ptr(unique_ptr&& u) noexcept;
Requires: If
D is not a reference type,
D shall satisfy the requirements of
MoveConstructible
(Table
23)
. Construction
of the deleter from an rvalue of type
D shall not
throw an exception
.Effects: Constructs a
unique_ptr by transferring ownership from
u to
*this. If
D is a reference type, this
deleter is copy constructed from
u's deleter; otherwise, this
deleter is move constructed from
u's deleter
. [
Note: The
deleter constructor can be implemented with
std::forward<D>. —
end note ]
Postconditions: get() yields the value
u.get()
yielded before the construction
. get_deleter() returns a reference
to the stored deleter that was constructed from
u.get_deleter(). If
D is a reference type then
get_deleter() and
u.get_deleter() both reference
the same lvalue deleter
.template <class U, class E> unique_ptr(unique_ptr<U, E>&& u) noexcept;
Requires: If
E is not a reference type,
construction of the deleter from an rvalue of type
E shall be well formed and shall not throw an exception
. Otherwise,
E is a reference type and construction of the deleter from an
lvalue of type
E shall be well formed and shall not throw an exception
.Remarks: This constructor shall not participate in overload resolution unless:
unique_ptr<U, E>::pointer is implicitly convertible to pointer,
U is not an array type, and
either
D is a reference type and
E is the same type as
D, or
D is not a reference type and
E is implicitly convertible to
D.
Effects: Constructs a
unique_ptr by transferring ownership from
u
to
*this. If
E is a reference type, this deleter is copy constructed from
u's deleter; otherwise, this deleter is move constructed from
u's
deleter
. [
Note: The deleter constructor can be implemented with
std::forward<E>. —
end note ]
Postconditions: get() yields the value
u.get()
yielded before the construction
. get_deleter() returns a reference
to the stored deleter that was constructed from
u.get_deleter(). ~unique_ptr();
Requires: The expression
get_deleter()(get()) shall be well formed,
shall have well-defined behavior, and shall not throw exceptions
. [
Note: The
use of
default_delete requires
T to be a complete type
. —
end note ]
Effects: If
get() == nullptr there are no effects
. Otherwise
get_deleter()(get()).unique_ptr& operator=(unique_ptr&& u) noexcept;
Requires: If
D is not a reference type,
D shall satisfy the
requirements of
MoveAssignable (Table
25) and assignment
of the deleter from an rvalue of type
D shall not throw an exception
. Otherwise,
D is a reference type;
remove_reference_t<D> shall satisfy the
CopyAssignable
requirements and assignment of the deleter from an
lvalue of type
D shall not throw an exception
.Effects:
Transfers ownership from
u to
*this as if by calling
reset(u.release()) followed by
get_deleter() = std::forward<D>(u.get_deleter()). template <class U, class E> unique_ptr& operator=(unique_ptr<U, E>&& u) noexcept;
Requires: If
E is not a reference type, assignment of the deleter from
an rvalue of type
E shall be well-formed and shall not throw an exception
. Otherwise,
E is a reference type and assignment of the deleter from an lvalue
of type
E shall be well-formed and shall not throw an exception
.Remarks: This operator shall not participate in overload resolution unless:
unique_ptr<U, E>::pointer is implicitly convertible to pointer, and
U is not an array type, and
is_assignable_v<D&, E&&> is
true.
Effects: Transfers ownership from
u to
*this as if by calling
reset(u.release()) followed by
get_deleter() = std::forward<E>(u.get_deleter()). unique_ptr& operator=(nullptr_t) noexcept;
Effects: As if by
reset(). Postconditions: get() == nullptr. add_lvalue_reference_t<T> operator*() const;
Requires: get() != nullptr. pointer operator->() const noexcept;
Requires: get() != nullptr. [
Note: The use of this function typically requires that
T be a complete type
. —
end note ]
pointer get() const noexcept;
Returns: The stored pointer
. deleter_type& get_deleter() noexcept;
const deleter_type& get_deleter() const noexcept;
Returns: A reference to the stored deleter
. explicit operator bool() const noexcept;
Returns: get() != nullptr. pointer release() noexcept;
Postconditions: get() == nullptr. Returns: The value
get() had at the start of
the call to
release. void reset(pointer p = pointer()) noexcept;
Requires: The expression
get_deleter()(get()) shall be well formed, shall have
well-defined behavior, and shall not throw exceptions
. Effects: Assigns
p to the stored pointer, and then if and only if the old value of the
stored pointer,
old_p, was not equal to
nullptr, calls
get_deleter()(old_p). [
Note: The order of these operations is significant
because the call to
get_deleter() may destroy
*this. —
end note ]
Postconditions: get() == p. [
Note: The postcondition does not hold if the call to
get_deleter()
destroys
*this since
this->get() is no longer a valid expression
. —
end note ]
void swap(unique_ptr& u) noexcept;
Effects: Invokes
swap on the stored pointers and on the stored
deleters of
*this and
u. template <class T, class D> void swap(unique_ptr<T, D>& x, unique_ptr<T, D>& y) noexcept;
Remarks: This function shall not participate in overload resolution
unless
is_swappable_v<D> is
true. Effects: Calls
x.swap(y). template <class T1, class D1, class T2, class D2>
bool operator==(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
Returns: x.get() == y.get(). template <class T1, class D1, class T2, class D2>
bool operator!=(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
Returns: x.get() != y.get(). template <class T1, class D1, class T2, class D2>
bool operator<(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
Requires: Let
CT denote
common_type_t<typename unique_ptr<T1, D1>::pointer,
typename unique_ptr<T2, D2>::pointer>
Then the specialization
less<CT> shall be a function object type (
[function.objects]) that
induces a strict weak ordering (
[alg.sorting]) on the pointer values
. Returns: less<CT>()(x.get(), y.get()). Remarks: If
unique_ptr<T1, D1>::pointer is not implicitly convertible
to
CT or
unique_ptr<T2, D2>::pointer is not implicitly
convertible to
CT, the program is ill-formed
. template <class T1, class D1, class T2, class D2>
bool operator<=(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template <class T1, class D1, class T2, class D2>
bool operator>(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template <class T1, class D1, class T2, class D2>
bool operator>=(const unique_ptr<T1, D1>& x, const unique_ptr<T2, D2>& y);
template <class T, class D>
bool operator==(const unique_ptr<T, D>& x, nullptr_t) noexcept;
template <class T, class D>
bool operator==(nullptr_t, const unique_ptr<T, D>& x) noexcept;
template <class T, class D>
bool operator!=(const unique_ptr<T, D>& x, nullptr_t) noexcept;
template <class T, class D>
bool operator!=(nullptr_t, const unique_ptr<T, D>& x) noexcept;
template <class T, class D>
bool operator<(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator<(nullptr_t, const unique_ptr<T, D>& x);
Requires: The specialization
less<unique_ptr<T, D>::pointer> shall be
a function object type (
[function.objects]) that induces a strict weak
ordering (
[alg.sorting]) on the pointer values
. Returns:
The first function template returns
less<unique_ptr<T, D>::pointer>()(x.get(),
nullptr). The second function template returns
less<unique_ptr<T, D>::pointer>()(nullptr, x.get()).template <class T, class D>
bool operator>(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator>(nullptr_t, const unique_ptr<T, D>& x);
Returns:
The first function template returns
nullptr < x. The second function template returns
x < nullptr.template <class T, class D>
bool operator<=(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator<=(nullptr_t, const unique_ptr<T, D>& x);
Returns:
The first function template returns
!(nullptr < x). The second function template returns
!(x < nullptr).template <class T, class D>
bool operator>=(const unique_ptr<T, D>& x, nullptr_t);
template <class T, class D>
bool operator>=(nullptr_t, const unique_ptr<T, D>& x);
Returns:
The first function template returns
!(x < nullptr). The second function template returns
!(nullptr < x).