std::atomic<std::weak_ptr> - cppreference.com

From cppreference.com

template<classT>structstd::atomic<std::weak_ptr<T>>;(since C++20)The partial template specialization of

std::atomic

for std::weak_ptr<T> allows users to manipulate weak_ptr objects atomically. T may be an incomplete type.

If multiple threads of execution access the same

std::weak_ptr

object without synchronization and any of those accesses uses a non-const member function of weak_ptr then a data race will occur unless all such access is performed through an instance of std::atomic<std::weak_ptr>.

Associated use_count increments are guaranteed to be part of the atomic operation. Associated use_count decrements are sequenced after the atomic operation, but are not required to be part of it, except for the use_count change when overriding expected in a failed CAS. Any associated deletion and deallocation are sequenced after the atomic update step and are not part of the atomic operation.

Note that the control block used by

std::weak_ptr

and

std::shared_ptr

is thread-safe: different non-atomic

std::weak_ptr

objects can be accessed using mutable operations, such as operator= or reset, simultaneously by multiple threads, even when these instances are copies or otherwise share the same control block internally.

Nested types

Type Definition value_typestd::weak_ptr<T>Member functions

All non-specialized

std::atomic

functions are also provided by this specialization, and no additional member functions.

atomic<weak_ptr<T>>::atomic

constexpratomic()noexcept=default; (1) atomic(std::weak_ptr<T>desired)noexcept; (2)(constexpr since C++26)atomic(constatomic&)=delete; (3) 1) Initializes the underlying weak_ptr<T> to default-constructed value.

2) Initializes the underlying weak_ptr<T> to a copy of desired. As with any

std::atomic

type, initialization is not an atomic operation.

3) Atomic types are not copy/move constructible.

atomic<weak_ptr<T>>::operator=

voidoperator=(constatomic&)=delete; (1) voidoperator=(std::weak_ptr<T>desired)noexcept; (2)(constexpr since C++26)1) Atomic types are not copy/move assignable.

2) Value assignment, equivalent to store(desired).

atomic<weak_ptr<T>>::is_lock_free

boolis_lock_free()constnoexcept;Returns true if the atomic operations on all objects of this type are lock-free, false otherwise.

atomic<weak_ptr<T>>::store

voidstore(std::weak_ptr<T>desired,std::memory_orderorder=std::memory_order_seq_cst)noexcept;(constexpr since C++26)Atomically replaces the value of *this with the value of desired as if by p.swap(desired) where p is the underlying std::weak_ptr<T>. Memory is ordered according to order.

If order is std::memory_order_consume, std::memory_order_acquire, or std::memory_order_acq_rel, the behavior is undefined.

atomic<weak_ptr<T>>::load

std::weak_ptr<T>load(std::memory_orderorder=std::memory_order_seq_cst)constnoexcept;(constexpr since C++26)Atomically returns a copy of the underlying std::weak_ptr<T>. Memory is ordered according to order.

If order is std::memory_order_release or std::memory_order_acq_rel, the behavior is undefined.

atomic<weak_ptr<T>>::operator std::weak_ptr<T>

operatorstd::weak_ptr<T>()constnoexcept;(constexpr since C++26)Equivalent to returnload();.

atomic<weak_ptr<T>>::exchange

std::weak_ptr<T>exchange(std::weak_ptr<T>desired,std::memory_orderorder=std::memory_order_seq_cst)noexcept;(constexpr since C++26)Atomically replaces the underlying std::weak_ptr<T> with desired as if by p.swap(desired) where p is the underlying std::weak_ptr<T>, and returns a copy of the value that p had immediately before the swap. Memory is ordered according to order. This is an atomic read-modify-write operation.

atomic<weak_ptr<T>>::compare_exchange_weak, compare_exchange_strong

boolcompare_exchange_strong(std::weak_ptr<T>&expected,std::weak_ptr<T>desired,std::memory_ordersuccess,std::memory_orderfailure)noexcept; (1)(constexpr since C++26)boolcompare_exchange_weak(std::weak_ptr<T>&expected,std::weak_ptr<T>desired,std::memory_ordersuccess,std::memory_orderfailure)noexcept; (2)(constexpr since C++26)boolcompare_exchange_strong(std::weak_ptr<T>&expected,std::weak_ptr<T>desired,std::memory_orderorder=std::memory_order_seq_cst)noexcept; (3)(constexpr since C++26)boolcompare_exchange_weak(std::weak_ptr<T>&expected,std::weak_ptr<T>desired,std::memory_orderorder=std::memory_order_seq_cst)noexcept; (4)(constexpr since C++26)1) If the underlying std::weak_ptr<T> stores the same pointer value as expected and shares ownership with it, or if both underlying and expected are empty, assigns from desired to the underlying std::weak_ptr<T>, returns true, and orders memory according to success, otherwise assigns from the underlying std::weak_ptr<T> to expected, returns false, and orders memory according to failure.

On success, the operation is an atomic read-modify-write operation on *this and expected is not accessed after the atomic update.

On failure, the operation is an atomic load operation on *this and expected is updated with the existing value read from the atomic object. This update to expected's use_count is part of this atomic operation, although the write itself (and any subsequent deallocation/destruction) is not required to be.

The behavior is undefined if failure is std::memory_order_release or std::memory_order_acq_rel.

2) Same as (1), but may also fail spuriously.

3) Equivalent to returncompare_exchange_strong(expected,desired,order,fail_order);, where fail_order is the same as order except that std::memory_order_acq_rel is replaced by std::memory_order_acquire and std::memory_order_release is replaced by std::memory_order_relaxed.

4) Equivalent to returncompare_exchange_weak(expected,desired,order,fail_order);, where fail_order is the same as order except that std::memory_order_acq_rel is replaced by std::memory_order_acquire and std::memory_order_release is replaced by std::memory_order_relaxed.

atomic<weak_ptr<T>>::wait

voidwait(std::weak_ptr<T>oldstd::memory_orderorder=std::memory_order_seq_cst)constnoexcept;(constexpr since C++26)Performs an atomic waiting operation.

Compares load(order) with old and if they are equivalent then blocks until *this is notified by notify_one() or notify_all(). This is repeated until load(order) changes. This function is guaranteed to return only if value has changed, even if underlying implementation unblocks spuriously. Memory is ordered according to order.

If order is std::memory_order_release or std::memory_order_acq_rel, the behavior is undefined.

Notes: two

std::weak_ptr

s are equivalent if they store the same pointer and either share ownership or are both empty.

atomic<weak_ptr<T>>::notify_one

voidnotify_one()noexcept;(constexpr since C++26)Performs an atomic notifying operation.

If there is a thread blocked in atomic waiting operations (i.e. wait()) on *this, then unblocks at least one such thread; otherwise does nothing.

atomic<weak_ptr<T>>::notify_all

voidnotify_all()noexcept;(constexpr since C++26)Performs an atomic notifying operation.

Unblocks all threads blocked in atomic waiting operations (i.e. wait()) on *this (if any).

Member constants

The only standard

std::atomic

member constant is_always_lock_free is also provided by this specialization.

atomic<weak_ptr<T>>::is_always_lock_free

staticconstexprboolis_always_lock_free=/* implementation-defined */;Notes

Feature-test

macro ValueStdFeature

__cpp_lib_constexpr_memory

202506L

(C++26)Constexpr std::atomic<std::weak_ptr>Example

See also

(C++11)

atomic class template and specializations for bool, integral, floating-point,(since C++20) and pointer types
(class template)

[edit]