pair.h 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635
  1. //===----------------------------------------------------------------------===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. #ifndef _LIBCPP___UTILITY_PAIR_H
  9. #define _LIBCPP___UTILITY_PAIR_H
  10. #include <__compare/common_comparison_category.h>
  11. #include <__compare/synth_three_way.h>
  12. #include <__config>
  13. #include <__functional/unwrap_ref.h>
  14. #include <__tuple>
  15. #include <__utility/forward.h>
  16. #include <__utility/move.h>
  17. #include <__utility/piecewise_construct.h>
  18. #include <cstddef>
  19. #include <type_traits>
  20. #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
  21. # pragma GCC system_header
  22. #endif
  23. _LIBCPP_BEGIN_NAMESPACE_STD
  24. #if defined(_LIBCPP_DEPRECATED_ABI_DISABLE_PAIR_TRIVIAL_COPY_CTOR)
  25. template <class, class>
  26. struct __non_trivially_copyable_base {
  27. _LIBCPP_CONSTEXPR _LIBCPP_INLINE_VISIBILITY
  28. __non_trivially_copyable_base() _NOEXCEPT {}
  29. _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
  30. __non_trivially_copyable_base(__non_trivially_copyable_base const&) _NOEXCEPT {}
  31. };
  32. #endif
  33. template <class _T1, class _T2>
  34. struct _LIBCPP_TEMPLATE_VIS pair
  35. #if defined(_LIBCPP_DEPRECATED_ABI_DISABLE_PAIR_TRIVIAL_COPY_CTOR)
  36. : private __non_trivially_copyable_base<_T1, _T2>
  37. #endif
  38. {
  39. typedef _T1 first_type;
  40. typedef _T2 second_type;
  41. _T1 first;
  42. _T2 second;
  43. #if !defined(_LIBCPP_CXX03_LANG)
  44. pair(pair const&) = default;
  45. pair(pair&&) = default;
  46. #else
  47. // Use the implicitly declared copy constructor in C++03
  48. #endif
  49. #ifdef _LIBCPP_CXX03_LANG
  50. _LIBCPP_INLINE_VISIBILITY
  51. pair() : first(), second() {}
  52. _LIBCPP_INLINE_VISIBILITY
  53. pair(_T1 const& __t1, _T2 const& __t2) : first(__t1), second(__t2) {}
  54. template <class _U1, class _U2>
  55. _LIBCPP_INLINE_VISIBILITY
  56. pair(const pair<_U1, _U2>& __p) : first(__p.first), second(__p.second) {}
  57. _LIBCPP_INLINE_VISIBILITY
  58. pair& operator=(pair const& __p) {
  59. first = __p.first;
  60. second = __p.second;
  61. return *this;
  62. }
  63. #else
  64. template<bool _Dummy = true, int&... _Args>
  65. struct _EnableImplicitDefaultConstructor {
  66. static constexpr bool value = __is_implicitly_default_constructible<_T1>::value
  67. && __is_implicitly_default_constructible<_T2>::value;
  68. };
  69. template<bool _Dummy = true, int&... _Args>
  70. struct _EnableExplicitDefaultConstructor {
  71. static constexpr bool value = is_default_constructible<_T1>::value
  72. && is_default_constructible<_T2>::value
  73. && !_EnableImplicitDefaultConstructor<_Dummy, _Args...>::value;
  74. };
  75. template <class _U1, class _U2, bool _Dummy = true>
  76. struct _EnableExplicitConstructor {
  77. static constexpr bool value = is_constructible<first_type, _U1>::value
  78. && is_constructible<second_type, _U2>::value
  79. && (!is_convertible<_U1, first_type>::value
  80. || !is_convertible<_U2, second_type>::value);
  81. };
  82. template <class _U1, class _U2, bool _Dummy = true>
  83. struct _EnableImplicitConstructor {
  84. static constexpr bool value = is_constructible<first_type, _U1>::value
  85. && is_constructible<second_type, _U2>::value
  86. && is_convertible<_U1, first_type>::value
  87. && is_convertible<_U2, second_type>::value;
  88. };
  89. template <class _Tuple, bool _Enable = __tuple_like_with_size<_Tuple, 2>::value
  90. && !is_same<typename decay<_Tuple>::type, pair>::value>
  91. struct _EnableImplicitTupleLikeConstructor {
  92. static constexpr bool value = false;
  93. };
  94. template <class _Tuple, bool _Enable = __tuple_like_with_size<_Tuple, 2>::value
  95. && !is_same<typename decay<_Tuple>::type, pair>::value>
  96. struct _EnableExplicitTupleLikeConstructor {
  97. static constexpr bool value = false;
  98. };
  99. template <class _Tuple, bool _Enable = __tuple_like_with_size<_Tuple, 2>::value
  100. && !is_same<typename decay<_Tuple>::type, pair>::value>
  101. struct _EnableTupleLikeAssign {
  102. static constexpr bool value = false;
  103. };
  104. template <class _Tuple>
  105. struct _EnableImplicitTupleLikeConstructor<_Tuple, true> {
  106. static constexpr bool value = __tuple_convertible<_Tuple, pair>::value;
  107. };
  108. template <class _Tuple>
  109. struct _EnableExplicitTupleLikeConstructor<_Tuple, true> {
  110. static constexpr bool value = __tuple_constructible<_Tuple, pair>::value
  111. && !__tuple_convertible<_Tuple, pair>::value;
  112. };
  113. template <class _Tuple>
  114. struct _EnableTupleLikeAssign<_Tuple, true> {
  115. static constexpr bool value = __tuple_assignable<_Tuple, pair>::value;
  116. };
  117. template<bool _Dummy = true, typename enable_if<
  118. _EnableExplicitDefaultConstructor<_Dummy>::value
  119. >::type* = nullptr>
  120. explicit _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
  121. pair()
  122. // danlark@ if you remove this define, MSVC gets into ICE
  123. #if !defined(_LIBCPP_COMPILER_MSVC)
  124. _NOEXCEPT_(is_nothrow_default_constructible<first_type>::value &&
  125. is_nothrow_default_constructible<second_type>::value)
  126. #endif
  127. : first(), second() {}
  128. template<bool _Dummy = true, typename enable_if<
  129. _EnableImplicitDefaultConstructor<_Dummy>::value
  130. >::type* = nullptr>
  131. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
  132. pair()
  133. // danlark@ if you remove this define, MSVC gets into ICE
  134. #if !defined(_LIBCPP_COMPILER_MSVC)
  135. _NOEXCEPT_(is_nothrow_default_constructible<first_type>::value &&
  136. is_nothrow_default_constructible<second_type>::value)
  137. #endif
  138. : first(), second() {}
  139. template <bool _Dummy = true, typename enable_if<
  140. _EnableExplicitConstructor<_T1 const&, _T2 const&, _Dummy>::value
  141. >::type* = nullptr>
  142. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  143. explicit pair(_T1 const& __t1, _T2 const& __t2)
  144. _NOEXCEPT_(is_nothrow_copy_constructible<first_type>::value &&
  145. is_nothrow_copy_constructible<second_type>::value)
  146. : first(__t1), second(__t2) {}
  147. template<bool _Dummy = true, bool _Dummy2 = true, typename enable_if<
  148. _EnableImplicitConstructor<_T1 const&, _T2 const&, _Dummy>::value
  149. >::type* = nullptr>
  150. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  151. pair(_T1 const& __t1, _T2 const& __t2)
  152. _NOEXCEPT_(is_nothrow_copy_constructible<first_type>::value &&
  153. is_nothrow_copy_constructible<second_type>::value)
  154. : first(__t1), second(__t2) {}
  155. template <
  156. #if _LIBCPP_STD_VER > 20 // http://wg21.link/P1951
  157. class _U1 = _T1, class _U2 = _T2,
  158. #else
  159. class _U1, class _U2,
  160. #endif
  161. typename enable_if<_EnableExplicitConstructor<_U1, _U2>::value>::type* = nullptr
  162. >
  163. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  164. explicit pair(_U1&& __u1, _U2&& __u2)
  165. _NOEXCEPT_((is_nothrow_constructible<first_type, _U1>::value &&
  166. is_nothrow_constructible<second_type, _U2>::value))
  167. : first(_VSTD::forward<_U1>(__u1)), second(_VSTD::forward<_U2>(__u2)) {}
  168. template<
  169. #if _LIBCPP_STD_VER > 20 // http://wg21.link/P1951
  170. class _U1 = _T1, class _U2 = _T2,
  171. #else
  172. class _U1, class _U2,
  173. #endif
  174. bool _Dummy = true, typename enable_if<_EnableImplicitConstructor<_U1, _U2, _Dummy>::value>::type* = nullptr
  175. >
  176. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  177. pair(_U1&& __u1, _U2&& __u2)
  178. _NOEXCEPT_((is_nothrow_constructible<first_type, _U1>::value &&
  179. is_nothrow_constructible<second_type, _U2>::value))
  180. : first(_VSTD::forward<_U1>(__u1)), second(_VSTD::forward<_U2>(__u2)) {}
  181. template<class _U1, class _U2, typename enable_if<
  182. _EnableExplicitConstructor<_U1 const&, _U2 const&>::value
  183. >::type* = nullptr>
  184. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  185. explicit pair(pair<_U1, _U2> const& __p)
  186. _NOEXCEPT_((is_nothrow_constructible<first_type, _U1 const&>::value &&
  187. is_nothrow_constructible<second_type, _U2 const&>::value))
  188. : first(__p.first), second(__p.second) {}
  189. template<class _U1, class _U2, bool _Dummy = true, typename enable_if<
  190. _EnableImplicitConstructor<_U1 const&, _U2 const&, _Dummy>::value
  191. >::type* = nullptr>
  192. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  193. pair(pair<_U1, _U2> const& __p)
  194. _NOEXCEPT_((is_nothrow_constructible<first_type, _U1 const&>::value &&
  195. is_nothrow_constructible<second_type, _U2 const&>::value))
  196. : first(__p.first), second(__p.second) {}
  197. template<class _U1, class _U2, typename enable_if<
  198. _EnableExplicitConstructor<_U1, _U2>::value
  199. >::type* = nullptr>
  200. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  201. explicit pair(pair<_U1, _U2>&&__p)
  202. _NOEXCEPT_((is_nothrow_constructible<first_type, _U1&&>::value &&
  203. is_nothrow_constructible<second_type, _U2&&>::value))
  204. : first(_VSTD::forward<_U1>(__p.first)), second(_VSTD::forward<_U2>(__p.second)) {}
  205. template<class _U1, class _U2, bool _Dummy = true, typename enable_if<
  206. _EnableImplicitConstructor<_U1, _U2>::value
  207. >::type* = nullptr>
  208. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  209. pair(pair<_U1, _U2>&& __p)
  210. _NOEXCEPT_((is_nothrow_constructible<first_type, _U1&&>::value &&
  211. is_nothrow_constructible<second_type, _U2&&>::value))
  212. : first(_VSTD::forward<_U1>(__p.first)), second(_VSTD::forward<_U2>(__p.second)) {}
  213. template<class _Tuple, typename enable_if<
  214. _EnableExplicitTupleLikeConstructor<_Tuple>::value
  215. >::type* = nullptr>
  216. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  217. explicit pair(_Tuple&& __p)
  218. : first(_VSTD::get<0>(_VSTD::forward<_Tuple>(__p))),
  219. second(_VSTD::get<1>(_VSTD::forward<_Tuple>(__p))) {}
  220. template<class _Tuple, bool _Dummy = true, typename enable_if<
  221. _EnableImplicitTupleLikeConstructor<_Tuple>::value
  222. >::type* = nullptr>
  223. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  224. pair(_Tuple&& __p)
  225. : first(_VSTD::get<0>(_VSTD::forward<_Tuple>(__p))),
  226. second(_VSTD::get<1>(_VSTD::forward<_Tuple>(__p))) {}
  227. template <class... _Args1, class... _Args2>
  228. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
  229. pair(piecewise_construct_t __pc,
  230. tuple<_Args1...> __first_args, tuple<_Args2...> __second_args)
  231. _NOEXCEPT_((is_nothrow_constructible<first_type, _Args1...>::value &&
  232. is_nothrow_constructible<second_type, _Args2...>::value))
  233. : pair(__pc, __first_args, __second_args,
  234. typename __make_tuple_indices<sizeof...(_Args1)>::type(),
  235. typename __make_tuple_indices<sizeof...(_Args2) >::type()) {}
  236. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
  237. pair& operator=(typename conditional<
  238. is_copy_assignable<first_type>::value &&
  239. is_copy_assignable<second_type>::value,
  240. pair, __nat>::type const& __p)
  241. _NOEXCEPT_(is_nothrow_copy_assignable<first_type>::value &&
  242. is_nothrow_copy_assignable<second_type>::value)
  243. {
  244. first = __p.first;
  245. second = __p.second;
  246. return *this;
  247. }
  248. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
  249. pair& operator=(typename conditional<
  250. is_move_assignable<first_type>::value &&
  251. is_move_assignable<second_type>::value,
  252. pair, __nat>::type&& __p)
  253. _NOEXCEPT_(is_nothrow_move_assignable<first_type>::value &&
  254. is_nothrow_move_assignable<second_type>::value)
  255. {
  256. first = _VSTD::forward<first_type>(__p.first);
  257. second = _VSTD::forward<second_type>(__p.second);
  258. return *this;
  259. }
  260. template <class _Tuple, bool _Dummy = true, typename enable_if<
  261. _EnableTupleLikeAssign<_Tuple>::value
  262. >::type* = nullptr>
  263. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
  264. pair& operator=(_Tuple&& __p) {
  265. first = _VSTD::get<0>(_VSTD::forward<_Tuple>(__p));
  266. second = _VSTD::get<1>(_VSTD::forward<_Tuple>(__p));
  267. return *this;
  268. }
  269. #endif
  270. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
  271. void
  272. swap(pair& __p) _NOEXCEPT_(__is_nothrow_swappable<first_type>::value &&
  273. __is_nothrow_swappable<second_type>::value)
  274. {
  275. using _VSTD::swap;
  276. swap(first, __p.first);
  277. swap(second, __p.second);
  278. }
  279. private:
  280. #ifndef _LIBCPP_CXX03_LANG
  281. template <class... _Args1, class... _Args2, size_t... _I1, size_t... _I2>
  282. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
  283. pair(piecewise_construct_t,
  284. tuple<_Args1...>& __first_args, tuple<_Args2...>& __second_args,
  285. __tuple_indices<_I1...>, __tuple_indices<_I2...>);
  286. #endif
  287. };
  288. #if _LIBCPP_STD_VER > 14
  289. template<class _T1, class _T2>
  290. pair(_T1, _T2) -> pair<_T1, _T2>;
  291. #endif
  292. // [pairs.spec], specialized algorithms
  293. template <class _T1, class _T2>
  294. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  295. bool
  296. operator==(const pair<_T1,_T2>& __x, const pair<_T1,_T2>& __y)
  297. {
  298. return __x.first == __y.first && __x.second == __y.second;
  299. }
  300. #if !defined(_LIBCPP_HAS_NO_CONCEPTS)
  301. template <class _T1, class _T2>
  302. _LIBCPP_HIDE_FROM_ABI constexpr
  303. common_comparison_category_t<
  304. __synth_three_way_result<_T1>,
  305. __synth_three_way_result<_T2> >
  306. operator<=>(const pair<_T1,_T2>& __x, const pair<_T1,_T2>& __y)
  307. {
  308. if (auto __c = _VSTD::__synth_three_way(__x.first, __y.first); __c != 0) {
  309. return __c;
  310. }
  311. return _VSTD::__synth_three_way(__x.second, __y.second);
  312. }
  313. #else // !defined(_LIBCPP_HAS_NO_CONCEPTS)
  314. template <class _T1, class _T2>
  315. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  316. bool
  317. operator!=(const pair<_T1,_T2>& __x, const pair<_T1,_T2>& __y)
  318. {
  319. return !(__x == __y);
  320. }
  321. template <class _T1, class _T2>
  322. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  323. bool
  324. operator< (const pair<_T1,_T2>& __x, const pair<_T1,_T2>& __y)
  325. {
  326. return __x.first < __y.first || (!(__y.first < __x.first) && __x.second < __y.second);
  327. }
  328. template <class _T1, class _T2>
  329. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  330. bool
  331. operator> (const pair<_T1,_T2>& __x, const pair<_T1,_T2>& __y)
  332. {
  333. return __y < __x;
  334. }
  335. template <class _T1, class _T2>
  336. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  337. bool
  338. operator>=(const pair<_T1,_T2>& __x, const pair<_T1,_T2>& __y)
  339. {
  340. return !(__x < __y);
  341. }
  342. template <class _T1, class _T2>
  343. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  344. bool
  345. operator<=(const pair<_T1,_T2>& __x, const pair<_T1,_T2>& __y)
  346. {
  347. return !(__y < __x);
  348. }
  349. #endif // !defined(_LIBCPP_HAS_NO_CONCEPTS)
  350. #if _LIBCPP_STD_VER > 20 && !defined(_LIBCPP_HAS_NO_CONCEPTS)
  351. template <class _T1, class _T2, class _U1, class _U2, template<class> class _TQual, template<class> class _UQual>
  352. requires requires { typename pair<common_reference_t<_TQual<_T1>, _UQual<_U1>>,
  353. common_reference_t<_TQual<_T2>, _UQual<_U2>>>; }
  354. struct basic_common_reference<pair<_T1, _T2>, pair<_U1, _U2>, _TQual, _UQual> {
  355. using type = pair<common_reference_t<_TQual<_T1>, _UQual<_U1>>,
  356. common_reference_t<_TQual<_T2>, _UQual<_U2>>>;
  357. };
  358. template <class _T1, class _T2, class _U1, class _U2>
  359. requires requires { typename pair<common_type_t<_T1, _U1>, common_type_t<_T2, _U2>>; }
  360. struct common_type<pair<_T1, _T2>, pair<_U1, _U2>> {
  361. using type = pair<common_type_t<_T1, _U1>, common_type_t<_T2, _U2>>;
  362. };
  363. #endif // _LIBCPP_STD_VER > 20 && !defined(_LIBCPP_HAS_NO_CONCEPTS)
  364. template <class _T1, class _T2>
  365. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX17
  366. typename enable_if
  367. <
  368. __is_swappable<_T1>::value &&
  369. __is_swappable<_T2>::value,
  370. void
  371. >::type
  372. swap(pair<_T1, _T2>& __x, pair<_T1, _T2>& __y)
  373. _NOEXCEPT_((__is_nothrow_swappable<_T1>::value &&
  374. __is_nothrow_swappable<_T2>::value))
  375. {
  376. __x.swap(__y);
  377. }
  378. #ifndef _LIBCPP_CXX03_LANG
  379. template <class _T1, class _T2>
  380. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  381. pair<typename __unwrap_ref_decay<_T1>::type, typename __unwrap_ref_decay<_T2>::type>
  382. make_pair(_T1&& __t1, _T2&& __t2)
  383. {
  384. return pair<typename __unwrap_ref_decay<_T1>::type, typename __unwrap_ref_decay<_T2>::type>
  385. (_VSTD::forward<_T1>(__t1), _VSTD::forward<_T2>(__t2));
  386. }
  387. #else // _LIBCPP_CXX03_LANG
  388. template <class _T1, class _T2>
  389. inline _LIBCPP_INLINE_VISIBILITY
  390. pair<_T1,_T2>
  391. make_pair(_T1 __x, _T2 __y)
  392. {
  393. return pair<_T1, _T2>(__x, __y);
  394. }
  395. #endif // _LIBCPP_CXX03_LANG
  396. template <class _T1, class _T2>
  397. struct _LIBCPP_TEMPLATE_VIS tuple_size<pair<_T1, _T2> >
  398. : public integral_constant<size_t, 2> {};
  399. template <size_t _Ip, class _T1, class _T2>
  400. struct _LIBCPP_TEMPLATE_VIS tuple_element<_Ip, pair<_T1, _T2> >
  401. {
  402. static_assert(_Ip < 2, "Index out of bounds in std::tuple_element<std::pair<T1, T2>>");
  403. };
  404. template <class _T1, class _T2>
  405. struct _LIBCPP_TEMPLATE_VIS tuple_element<0, pair<_T1, _T2> >
  406. {
  407. typedef _LIBCPP_NODEBUG _T1 type;
  408. };
  409. template <class _T1, class _T2>
  410. struct _LIBCPP_TEMPLATE_VIS tuple_element<1, pair<_T1, _T2> >
  411. {
  412. typedef _LIBCPP_NODEBUG _T2 type;
  413. };
  414. template <size_t _Ip> struct __get_pair;
  415. template <>
  416. struct __get_pair<0>
  417. {
  418. template <class _T1, class _T2>
  419. static
  420. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  421. _T1&
  422. get(pair<_T1, _T2>& __p) _NOEXCEPT {return __p.first;}
  423. template <class _T1, class _T2>
  424. static
  425. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  426. const _T1&
  427. get(const pair<_T1, _T2>& __p) _NOEXCEPT {return __p.first;}
  428. #ifndef _LIBCPP_CXX03_LANG
  429. template <class _T1, class _T2>
  430. static
  431. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  432. _T1&&
  433. get(pair<_T1, _T2>&& __p) _NOEXCEPT {return _VSTD::forward<_T1>(__p.first);}
  434. template <class _T1, class _T2>
  435. static
  436. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  437. const _T1&&
  438. get(const pair<_T1, _T2>&& __p) _NOEXCEPT {return _VSTD::forward<const _T1>(__p.first);}
  439. #endif // _LIBCPP_CXX03_LANG
  440. };
  441. template <>
  442. struct __get_pair<1>
  443. {
  444. template <class _T1, class _T2>
  445. static
  446. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  447. _T2&
  448. get(pair<_T1, _T2>& __p) _NOEXCEPT {return __p.second;}
  449. template <class _T1, class _T2>
  450. static
  451. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  452. const _T2&
  453. get(const pair<_T1, _T2>& __p) _NOEXCEPT {return __p.second;}
  454. #ifndef _LIBCPP_CXX03_LANG
  455. template <class _T1, class _T2>
  456. static
  457. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  458. _T2&&
  459. get(pair<_T1, _T2>&& __p) _NOEXCEPT {return _VSTD::forward<_T2>(__p.second);}
  460. template <class _T1, class _T2>
  461. static
  462. _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  463. const _T2&&
  464. get(const pair<_T1, _T2>&& __p) _NOEXCEPT {return _VSTD::forward<const _T2>(__p.second);}
  465. #endif // _LIBCPP_CXX03_LANG
  466. };
  467. template <size_t _Ip, class _T1, class _T2>
  468. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  469. typename tuple_element<_Ip, pair<_T1, _T2> >::type&
  470. get(pair<_T1, _T2>& __p) _NOEXCEPT
  471. {
  472. return __get_pair<_Ip>::get(__p);
  473. }
  474. template <size_t _Ip, class _T1, class _T2>
  475. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  476. const typename tuple_element<_Ip, pair<_T1, _T2> >::type&
  477. get(const pair<_T1, _T2>& __p) _NOEXCEPT
  478. {
  479. return __get_pair<_Ip>::get(__p);
  480. }
  481. #ifndef _LIBCPP_CXX03_LANG
  482. template <size_t _Ip, class _T1, class _T2>
  483. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  484. typename tuple_element<_Ip, pair<_T1, _T2> >::type&&
  485. get(pair<_T1, _T2>&& __p) _NOEXCEPT
  486. {
  487. return __get_pair<_Ip>::get(_VSTD::move(__p));
  488. }
  489. template <size_t _Ip, class _T1, class _T2>
  490. inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11
  491. const typename tuple_element<_Ip, pair<_T1, _T2> >::type&&
  492. get(const pair<_T1, _T2>&& __p) _NOEXCEPT
  493. {
  494. return __get_pair<_Ip>::get(_VSTD::move(__p));
  495. }
  496. #endif // _LIBCPP_CXX03_LANG
  497. #if _LIBCPP_STD_VER > 11
  498. template <class _T1, class _T2>
  499. inline _LIBCPP_INLINE_VISIBILITY
  500. constexpr _T1 & get(pair<_T1, _T2>& __p) _NOEXCEPT
  501. {
  502. return __get_pair<0>::get(__p);
  503. }
  504. template <class _T1, class _T2>
  505. inline _LIBCPP_INLINE_VISIBILITY
  506. constexpr _T1 const & get(pair<_T1, _T2> const& __p) _NOEXCEPT
  507. {
  508. return __get_pair<0>::get(__p);
  509. }
  510. template <class _T1, class _T2>
  511. inline _LIBCPP_INLINE_VISIBILITY
  512. constexpr _T1 && get(pair<_T1, _T2>&& __p) _NOEXCEPT
  513. {
  514. return __get_pair<0>::get(_VSTD::move(__p));
  515. }
  516. template <class _T1, class _T2>
  517. inline _LIBCPP_INLINE_VISIBILITY
  518. constexpr _T1 const && get(pair<_T1, _T2> const&& __p) _NOEXCEPT
  519. {
  520. return __get_pair<0>::get(_VSTD::move(__p));
  521. }
  522. template <class _T1, class _T2>
  523. inline _LIBCPP_INLINE_VISIBILITY
  524. constexpr _T1 & get(pair<_T2, _T1>& __p) _NOEXCEPT
  525. {
  526. return __get_pair<1>::get(__p);
  527. }
  528. template <class _T1, class _T2>
  529. inline _LIBCPP_INLINE_VISIBILITY
  530. constexpr _T1 const & get(pair<_T2, _T1> const& __p) _NOEXCEPT
  531. {
  532. return __get_pair<1>::get(__p);
  533. }
  534. template <class _T1, class _T2>
  535. inline _LIBCPP_INLINE_VISIBILITY
  536. constexpr _T1 && get(pair<_T2, _T1>&& __p) _NOEXCEPT
  537. {
  538. return __get_pair<1>::get(_VSTD::move(__p));
  539. }
  540. template <class _T1, class _T2>
  541. inline _LIBCPP_INLINE_VISIBILITY
  542. constexpr _T1 const && get(pair<_T2, _T1> const&& __p) _NOEXCEPT
  543. {
  544. return __get_pair<1>::get(_VSTD::move(__p));
  545. }
  546. #endif
  547. _LIBCPP_END_NAMESPACE_STD
  548. #endif // _LIBCPP___UTILITY_PAIR_H