Created on 2019-07-10.00:00:00 last changed 45 months ago
Proposed resolution:
This wording is relative to N4835.
Modify [util.smartptr.shared.const] as indicated:
template<class Y, class D> shared_ptr(Y* p, D d); template<class Y, class D, class A> shared_ptr(Y* p, D d, A a); template<class D> shared_ptr(nullptr_t p, D d); template<class D, class A> shared_ptr(nullptr_t p, D d, A a);-?- Constraints: is_move_constructible_v<D> is true, and d(p) is a well-formed expression. For the first two overloads:
If T is an array type, then either T is U[N] and Y(*)[N] is convertible to T*, or T is U[] and Y(*)[] is convertible to T*.
If T is not an array type, then Y* is convertible to T*.
-9-
RequiresExpects: Construction of d and a deleter of type […][…]
-13- Remarks: When T is an array type, this constructor shall not participate in overload resolution unless is_move_constructible_v<D> is true, the expression d(p) is well-formed, and either T is U[N] and Y(*)[N] is convertible to T*, or T is U[] and Y(*)[] is convertible to T*. When T is not an array type, this constructor shall not participate in overload resolution unless is_move_constructible_v<D> is true, the expression d(p) is well-formed, and Y* is convertible to T*.
[ 2019-11-17 Issue Prioritization ]
Status to Tentatively Ready and priority to 0 after six positive votes on the reflector.
Issue 2875 added [util.smartptr.shared.const] paragraph 13:
Remarks: When T is an array type, this constructor shall not participate in overload resolution unless is_move_constructible_v<D> is true, the expression d(p) is well-formed, and either T is U[N] and Y(*)[N] is convertible to T*, or T is U[] and Y(*)[] is convertible to T*. When T is not an array type, this constructor shall not participate in overload resolution unless is_move_constructible_v<D> is true, the expression d(p) is well-formed, and Y* is convertible to T*.which pertains to the four constructor overloads:
which is fine (ignoring for now that two occurrences of "this constructor" should read "these constructors") for the two overloads with a template parameter Y, but not so much for the two with no such template parameter.template<class Y, class D> shared_ptr(Y* p, D d); template<class Y, class D, class A> shared_ptr(Y* p, D d, A a); template<class D> shared_ptr(nullptr_t p, D d); template<class D, class A> shared_ptr(nullptr_t p, D d, A a);
MSVC ignores the constraints on Y for the overloads with no such template parameter, whereas libstdc++ and libc++ seem to ignore all of the constraints for those overloads (See Compiler Explorer). We should fix the broken wording, ideally by requiring the MSVC interpretation - the nullptr_t constructors participate in overload resolution only when is_movable_v<D> is true and d(p) is well-formed - so concepts and traits that check constructibility are correct.
History | |||
---|---|---|---|
Date | User | Action | Args |
2021-02-25 10:48:01 | admin | set | status: wp -> c++20 |
2020-02-24 16:02:59 | admin | set | status: voting -> wp |
2020-01-17 04:54:50 | admin | set | status: ready -> voting |
2019-11-17 12:16:59 | admin | set | messages: + msg10824 |
2019-11-17 12:16:59 | admin | set | status: new -> ready |
2019-07-10 23:53:23 | admin | set | messages: + msg10479 |
2019-07-10 00:00:00 | admin | create |