Библиотека предоставляет шаблон для разнородных пар значений. Библиотека также предоставляет соответствующий шаблон функций для упрощения их построения и несколько шаблонов, которые обеспечивают доступ кpair объектам, как если бы они былиtuple объектами (см.[tuple.helper] И[tuple.elem]).
namespace std { template <class T1, class T2> struct pair { using first_type = T1; using second_type = T2; T1 first; T2 second; pair(const pair&) = default; pair(pair&&) = default; EXPLICIT constexpr pair(); EXPLICIT constexpr pair(const T1& x, const T2& y); template<class U1, class U2> EXPLICIT constexpr pair(U1&& x, U2&& y); template<class U1, class U2> EXPLICIT constexpr pair(const pair<U1, U2>& p); template<class U1, class U2> EXPLICIT constexpr pair(pair<U1, U2>&& p); template <class... Args1, class... Args2> pair(piecewise_construct_t, tuple<Args1...> first_args, tuple<Args2...> second_args); pair& operator=(const pair& p); template<class U1, class U2> pair& operator=(const pair<U1, U2>& p); pair& operator=(pair&& p) noexcept(see below); template<class U1, class U2> pair& operator=(pair<U1, U2>&& p); void swap(pair& p) noexcept(see below); }; template<class T1, class T2> pair(T1, T2) -> pair<T1, T2>; }
Конструкторы и функции-членыpair не должны вызывать исключения, если одна из поэлементных операций, указанных для вызова для этой операции, не вызывает исключение.
Конструктор перемещения и копирования по умолчанию, соответственно,pair должен быть функцией constexpr тогда и только тогда, когда все требуемые поэлементные инициализации для копирования и перемещения, соответственно, будут удовлетворять требованиям для функции constexpr. Деструкторpair должен быть тривиальным деструктором, если (is_trivially_destructible_v<T1> && is_trivially_destructible_v<T2>) естьtrue.
EXPLICIT constexpr pair();
Remarks: Этот конструктор не должен участвовать в разрешении перегрузки , если is_default_constructible_v<first_type> неtrue и is_default_constructible_v<second_type> являетсяtrue. [ Note: Это поведение может быть реализовано с помощью шаблона конструктора с аргументами шаблона по умолчанию. ] Конструктор является явным тогда и только тогда, когда любой из них или не является неявно конструктивным по умолчанию. [ Это поведение может быть реализовано с помощью трейта, который проверяет, можно ли инициализировать a или a . ] — end note first_type second_type Note: const first_type& const second_type&{} — end note
EXPLICIT constexpr pair(const T1& x, const T2& y);
Remarks: Этот конструктор не должен участвовать в разрешении перегрузки , еслиis_copy_constructible_v<first_type> неtrue и is_copy_constructible_v<second_type> являетсяtrue. Конструктор является явным тогда и только тогда, когда is_convertible_v<const first_type&, first_type> естьfalse или is_convertible_v<const second_type&, second_type> естьfalse.
template<class U1, class U2> EXPLICIT constexpr pair(U1&& x, U2&& y);
Effects: Инициализируетсяfirst с помощью std::forward<U1>(x) иsecond с помощьюstd::forward<U2>(y).
Remarks: Этот конструктор не должен участвовать в разрешении перегрузки , если is_constructible_v<first_type, U1&&> неtrue и is_constructible_v<second_type, U2&&> являетсяtrue. Конструктор является явным тогда и только тогда, когда is_convertible_v<U1&&, first_type> естьfalse или is_convertible_v<U2&&, second_type> естьfalse.
template<class U1, class U2> EXPLICIT constexpr pair(const pair<U1, U2>& p);
Remarks: Этот конструктор не должен участвовать в разрешении перегрузки , если is_constructible_v<first_type, const U1&> неtrue и is_constructible_v<second_type, const U2&> являетсяtrue. Конструктор является явным тогда и только тогда, когда is_convertible_v<const U1&, first_type> естьfalse или is_convertible_v<const U2&, second_type> естьfalse.
template<class U1, class U2> EXPLICIT constexpr pair(pair<U1, U2>&& p);
Effects: Инициализируетсяfirst с помощью std::forward<U1>(p.first) иsecond с помощью std::forward<U2>(p.second).
Remarks: Этот конструктор не должен участвовать в разрешении перегрузки , если is_constructible_v<first_type, U1&&> неtrue и is_constructible_v<second_type, U2&&> являетсяtrue. Конструктор является явным тогда и только тогда, когда is_convertible_v<U1&&, first_type> естьfalse или is_convertible_v<U2&&, second_type> естьfalse.
template<class... Args1, class... Args2>
pair(piecewise_construct_t, tuple<Args1...> first_args, tuple<Args2...> second_args);
Requires:is_constructible_v<first_type, Args1&&...> естьtrue иis_constructible_v<second_type, Args2&&...> естьtrue.
Effects: Инициализируетсяfirst аргументами типов, Args1... полученных путем пересылки элементов,first_args и инициализируетсяsecond аргументами типов,Args2... полученных пересылкой элементовsecond_args. (Здесь пересылка элементаx типаU внутриtuple объекта означает вызов std::forward<U>(x).) Вызывается эта форма конструкции, при которой аргументы конструктора дляfirst иsecond предоставляются в отдельном tuple объектеpiecewise construction.
pair& operator=(const pair& p);
Remarks: Этот оператор должен быть определен как удален , если is_copy_assignable_v<first_type> неtrue иis_copy_assignable_v<second_type> являетсяtrue.
template<class U1, class U2> pair& operator=(const pair<U1, U2>& p);
Remarks: Этот оператор не должен участвовать в разрешении перегрузки , если is_assignable_v<first_type&, const U1&> неtrue иis_assignable_v<second_type&, const U2&> являетсяtrue.
pair& operator=(pair&& p) noexcept(see below);
Effects:
Назначает кfirst сstd::forward<first_type>(p.first)
и кsecond с
std::forward<second_type>(p.second).
Remarks: Этот оператор должен быть определен как удален , если is_move_assignable_v<first_type> неtrue иis_move_assignable_v<second_type> являетсяtrue.
Remarks: Выражение внутриnoexcept эквивалентно:
is_nothrow_move_assignable_v<T1> && is_nothrow_move_assignable_v<T2>
template<class U1, class U2> pair& operator=(pair<U1, U2>&& p);
Remarks: Этот оператор не должен участвовать в разрешении перегрузки , если is_assignable_v<first_type&, U1&&> неtrue иis_assignable_v<second_type&, U2&&> являетсяtrue.
void swap(pair& p) noexcept(see below);
Requires: first должны бытьswappable with p.first иsecond должны быть замененыp.second.
template <class T1, class T2>
constexpr bool operator==(const pair<T1, T2>& x, const pair<T1, T2>& y);
template <class T1, class T2>
constexpr bool operator<(const pair<T1, T2>& x, const pair<T1, T2>& y);
template <class T1, class T2>
constexpr bool operator!=(const pair<T1, T2>& x, const pair<T1, T2>& y);
template <class T1, class T2>
constexpr bool operator>(const pair<T1, T2>& x, const pair<T1, T2>& y);
template <class T1, class T2>
constexpr bool operator>=(const pair<T1, T2>& x, const pair<T1, T2>& y);
template <class T1, class T2>
constexpr bool operator<=(const pair<T1, T2>& x, const pair<T1, T2>& y);
template<class T1, class T2> void swap(pair<T1, T2>& x, pair<T1, T2>& y)
noexcept(noexcept(x.swap(y)));
Remarks: Эта функция не будет участвовать в разрешении перегрузки , если is_swappable_v<T1> неtrue и is_swappable_v<T2> являетсяtrue.
template <class T1, class T2>
constexpr pair<V1, V2> make_pair(T1&& x, T2&& y);
Returns:pair<V1, V2>(std::forward<T1>(x), std::forward<T2>(y)), гдеV1 иV2 определяются следующим образом: ПустьUi будет decay_t<Ti> для каждогоTi. ЕслиUi является специализациейreference_wrapper, тоVi естьUi::type&, иначеVi -Ui.
template <class T1, class T2>
struct tuple_size<pair<T1, T2>> : integral_constant<size_t, 2> { };
tuple_element<0, pair<T1, T2>>::type
tuple_element<1, pair<T1, T2>>::type
template<size_t I, class T1, class T2>
constexpr tuple_element_t<I, pair<T1, T2>>& get(pair<T1, T2>& p) noexcept;
template<size_t I, class T1, class T2>
constexpr const tuple_element_t<I, pair<T1, T2>>& get(const pair<T1, T2>& p) noexcept;
template<size_t I, class T1, class T2>
constexpr tuple_element_t<I, pair<T1, T2>>&& get(pair<T1, T2>&& p) noexcept;
template<size_t I, class T1, class T2>
constexpr const tuple_element_t<I, pair<T1, T2>>&& get(const pair<T1, T2>&& p) noexcept;
Returns: ЕслиI == 0 возвращает ссылку наp.first; еслиI == 1 возвращает ссылку наp.second; в противном случае программа будет некорректной.
template <class T1, class T2>
constexpr T1& get(pair<T1, T2>& p) noexcept;
template <class T1, class T2>
constexpr const T1& get(const pair<T1, T2>& p) noexcept;
template <class T1, class T2>
constexpr T1&& get(pair<T1, T2>&& p) noexcept;
template <class T1, class T2>
constexpr const T1&& get(const pair<T1, T2>&& p) noexcept;
template <class T2, class T1>
constexpr T2& get(pair<T1, T2>& p) noexcept;
template <class T2, class T1>
constexpr const T2& get(const pair<T1, T2>& p) noexcept;
template <class T2, class T1>
constexpr T2&& get(pair<T1, T2>&& p) noexcept;
template <class T2, class T1>
constexpr const T2&& get(const pair<T1, T2>&& p) noexcept;
struct piecewise_construct_t {
explicit piecewise_construct_t() = default;
};
inline constexpr piecewise_construct_t piecewise_construct{};
Этоstructpiecewise_construct_t пустой структурный тип, используемый как уникальный тип для устранения неоднозначности перегрузки конструктора и функции. В частности, pair имеет конструктор сpiecewise_construct_t первым аргументом, за которым сразу следуют дваtuple аргумента, используемых для кусочного построения элементовpair объекта.