20 General utilities library [utilities]

20.5 Tuples [tuple]

20.5.2 Class template tuple [tuple.tuple]

20.5.2.1 Construction [tuple.cnstr]

For each tuple constructor, an exception is thrown only if the construction of one of the types in Types throws an exception.

The defaulted move and copy constructor, respectively, of tuple shall be a constexpr function if and only if all required element-wise initializations for copy and move, respectively, would satisfy the requirements for a constexpr function. The defaulted move and copy constructor of tuple<> shall be constexpr functions.

In the constructor descriptions that follow, let i be in the range [0, sizeof...(Types)) in order, Ti be the ith type in Types, and Ui be the ith type in a template parameter pack named UTypes, where indexing is zero-based.

EXPLICIT constexpr tuple();

Effects: Value-initializes each element.

Remarks: This constructor shall not participate in overload resolution unless is_default_constructible_v<Ti> is true for all i. [ Note: This behavior can be implemented by a constructor template with default template arguments.  — end note ] The constructor is explicit if and only if Ti is not implicitly default-constructible for at least one i. [ Note: This behavior can be implemented with a trait that checks whether a const Ti& can be initialized with {}.  — end note ]

EXPLICIT constexpr tuple(const Types&...);

Effects: The constructor initializes each element with the value of the corresponding parameter.

Remarks: This constructor shall not participate in overload resolution unless sizeof...(Types) >= 1 and is_copy_constructible_v<Ti> is true for all i. The constructor is explicit if and only if is_convertible_v<const Ti&, Ti> is false for at least one i.

template <class... UTypes> EXPLICIT constexpr tuple(UTypes&&... u);

Effects: The constructor initializes the elements in the tuple with the corresponding value in std::forward<UTypes>(u).

Remarks: This constructor shall not participate in overload resolution unless sizeof...(Types) == sizeof...(UTypes) and sizeof...(Types) >= 1 and is_constructible_v<Ti, Ui&&> is true for all i. The constructor is explicit if and only if is_convertible_v<Ui&&, Ti> is false for at least one i.

tuple(const tuple& u) = default;

Requires: is_copy_constructible_v<Ti> is true for all i.

Effects: Initializes each element of *this with the corresponding element of u.

tuple(tuple&& u) = default;

Requires: is_move_constructible_v<Ti> is true for all i.

Effects: For all i, initializes the ith element of *this with std::forward<Ti>(get<i>(u)).

template <class... UTypes> EXPLICIT constexpr tuple(const tuple<UTypes...>& u);

Effects: The constructor initializes each element of *this with the corresponding element of u.

Remarks: This constructor shall not participate in overload resolution unless

  • sizeof...(Types) == sizeof...(UTypes) and

  • is_constructible_v<Ti, const Ui&> is true for all i, and

  • sizeof...(Types) != 1, or (when Types... expands to T and UTypes... expands to U) !is_convertible_v<const tuple<U>&, T> && !is_constructible_v<T, const tuple<U>&>&& !is_same_v<T, U> is true.

The constructor is explicit if and only if is_convertible_v<const Ui&, Ti> is false for at least one i.

template <class... UTypes> EXPLICIT constexpr tuple(tuple<UTypes...>&& u);

Effects: For all i, the constructor initializes the ith element of *this with std::forward<Ui>(get<i>(u)).

Remarks: This constructor shall not participate in overload resolution unless

  • sizeof...(Types) == sizeof...(UTypes), and

  • is_constructible_v<Ti, Ui&&> is true for all i, and

  • sizeof...(Types) != 1, or (when Types... expands to T and UTypes... expands to U) !is_convertible_v<tuple<U>, T> && !is_constructible_v<T, tuple<U>> &&!is_same_v<T, U> is true.

The constructor is explicit if and only if is_convertible_v<Ui&&, Ti> is false for at least one i.

template <class U1, class U2> EXPLICIT constexpr tuple(const pair<U1, U2>& u);

Effects: The constructor initializes the first element with u.first and the second element with u.second.

Remarks: This constructor shall not participate in overload resolution unless sizeof...(Types) == 2, is_constructible_v<T0, const U1&> is true and is_constructible_v<T1, const U2&> is true.

The constructor is explicit if and only if is_convertible_v<const U1&, T0> is false or is_convertible_v<const U2&, T1> is false.

template <class U1, class U2> EXPLICIT constexpr tuple(pair<U1, U2>&& u);

Effects: The constructor initializes the first element with std::forward<U1>(u.first) and the second element with std::forward<U2>(u.second).

Remarks: This constructor shall not participate in overload resolution unless sizeof...(Types) == 2, is_constructible_v<T0, U1&&> is true and is_constructible_v<T1, U2&&> is true.

The constructor is explicit if and only if is_convertible_v<U1&&, T0> is false or is_convertible_v<U2&&, T1> is false.

template <class Alloc> tuple(allocator_arg_t, const Alloc& a); template <class Alloc> EXPLICIT tuple(allocator_arg_t, const Alloc& a, const Types&...); template <class Alloc, class... UTypes> EXPLICIT tuple(allocator_arg_t, const Alloc& a, UTypes&&...); template <class Alloc> tuple(allocator_arg_t, const Alloc& a, const tuple&); template <class Alloc> tuple(allocator_arg_t, const Alloc& a, tuple&&); template <class Alloc, class... UTypes> EXPLICIT tuple(allocator_arg_t, const Alloc& a, const tuple<UTypes...>&); template <class Alloc, class... UTypes> EXPLICIT tuple(allocator_arg_t, const Alloc& a, tuple<UTypes...>&&); template <class Alloc, class U1, class U2> EXPLICIT tuple(allocator_arg_t, const Alloc& a, const pair<U1, U2>&); template <class Alloc, class U1, class U2> EXPLICIT tuple(allocator_arg_t, const Alloc& a, pair<U1, U2>&&);

Requires: Alloc shall meet the requirements for an Allocator ([allocator.requirements]).

Effects: Equivalent to the preceding constructors except that each element is constructed with uses-allocator construction ([allocator.uses.construction]).