This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of C++20 status.
tuple(allocator_arg_t, const Alloc&)
should be conditionally explicitSection: 22.4.4.2 [tuple.cnstr] Status: C++20 Submitter: Jonathan Wakely Opened: 2018-08-21 Last modified: 2021-02-25
Priority: 3
View other active issues in [tuple.cnstr].
View all other issues in [tuple.cnstr].
View all issues with C++20 status.
Discussion:
std::tuple
's allocator-extended constructors say "Effects: Equivalent to the preceding constructors except
that each element is constructed with uses-allocator construction". That's not true for the first one, as shown by:
#include <tuple> struct X { explicit X() { } }; std::tuple<X> f() { return {}; } std::tuple<X> g() { return { std::allocator_arg, std::allocator<int>{} }; }
The function f()
doesn't compile because of the explicit constructor, but g()
does, despite using the
same constructor for X
. The conditional explicit-ness is not equivalent.
[2018-09 Reflector prioritization]
Set Priority to 3
[2019-02; Kona Wednesday night issue processing]
Status to Ready
Proposed resolution:
This wording is relative to N4762.
Modify 22.4.4 [tuple.tuple], class template tuple
synopsis, as indicated:
[…] // allocator-extended constructors template<class Alloc> explicit(see below) tuple(allocator_arg_t, const Alloc& a); template<class Alloc> explicit(see below) tuple(allocator_arg_t, const Alloc& a, const Types&...); […]
Modify 22.4.4.2 [tuple.cnstr], as indicated:
explicit(see below) constexpr tuple();-5- Effects: Value-initializes each element.
-6- Remarks: This constructor shall not participate in overload resolution unlessis_default_constructible_v<Ti>
istrue
for alli
. [Note: This behavior can be implemented by a constructor template with default template arguments. — end note] The expression insideexplicit
evaluates totrue
if and only ifTi
is notimplicitly default-constructiblecopy-list-initializable from an empty list for at least onei
. [Note: This behavior can be implemented with a trait that checks whether aconst Ti&
can be initialized with{}
. — end note][…]
template<class Alloc> explicit(see below) tuple(allocator_arg_t, const Alloc& a); template<class Alloc> explicit(see below) tuple(allocator_arg_t, const Alloc& a, const Types&...); […] template<class Alloc, class U1, class U2> explicit(see below) tuple(allocator_arg_t, const Alloc& a, pair<U1, U2>&&);-25- Requires:
[…]Alloc
shall satisfy theCpp17Allocator
requirements (Table 33).