Created on 2025-08-24.00:00:00 last changed 5 days ago
Proposed resolution:
This wording is relative to N5014.
Modify [unique.ptr.single.observers] as indicated:
constexpr add_lvalue_reference_t<T> operator*() const noexcept(noexcept(*declval<pointer>()));-?- Constraints: *declval<pointer>() is a well-formed expression.
-1- Mandates: reference_converts_from_temporary_v<add_lvalue_reference_t<T>, decltype(*declval<pointer>())> is `false`. -2- Preconditions: `get() != nullptr` is `true`. -3- Returns: `*get()`.
[ 2025-08-26; Reflector discussion ]
During reflector triaging it had been pointed out that a better solution would be to constrain the `operator*` directly. The proposed wording has been updated to that effect.
LWG 2762 added a conditional `noexcept` specification to `unique_ptr::operator*` to make it consistent with `shared_ptr::operator*`:
constexpr add_lvalue_reference_t<T> operator*() const noexcept(noexcept(*declval<pointer>()));
This unexpectedly makes unique_ptr<void>::operator*
no longer SFINAE-friendly,
for example:
#include <memory>
template<class T> concept dereferenceable = requires(T& t) { *t; };
static_assert( dereferenceable<int *>);
static_assert(!dereferenceable<void*>);
static_assert( dereferenceable<std::shared_ptr<int >>);
static_assert(!dereferenceable<std::shared_ptr<void>>);
static_assert( dereferenceable<std::unique_ptr<int >>);
static_assert( dereferenceable<std::unique_ptr<void>>); // hard error
Given that the standard intends for `operator*` of `shared_ptr` and `unique_ptr` to be SFINAE-friendly based on [util.smartptr.shared.obs], regardless of the value of `static_assert`, it is reasonable to assume that there should be no hard error here.
This wording is relative to N5014.
Modify [unique.ptr.single.observers] as indicated:
constexpr add_lvalue_reference_t<T> operator*() const noexcept(noexcept(*declval<pointer>())see below);-1- Mandates: reference_converts_from_temporary_v<add_lvalue_reference_t<T>, decltype(*declval<pointer>())> is `false`.
-2- Preconditions: `get() != nullptr` is `true`. -3- Returns: `*get()`. -?- Remarks:: The exception specification is equivalent to:!requires { *declval<pointer>(); } || requires { { *declval<pointer>() } noexcept; }
History | |||
---|---|---|---|
Date | User | Action | Args |
2025-08-26 17:06:01 | admin | set | messages: + msg14965 |
2025-08-24 13:24:52 | admin | set | messages: + msg14954 |
2025-08-24 00:00:00 | admin | create |