1// -*- C++ -*- 2//===--------------------------- tuple ------------------------------------===// 3// 4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 5// See https://llvm.org/LICENSE.txt for license information. 6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 7// 8//===----------------------------------------------------------------------===// 9 10#ifndef _LIBCPP_TUPLE 11#define _LIBCPP_TUPLE 12 13/* 14 tuple synopsis 15 16namespace std 17{ 18 19template <class... T> 20class tuple { 21public: 22 constexpr tuple(); 23 explicit tuple(const T&...); // constexpr in C++14 24 template <class... U> 25 explicit tuple(U&&...); // constexpr in C++14 26 tuple(const tuple&) = default; 27 tuple(tuple&&) = default; 28 template <class... U> 29 tuple(const tuple<U...>&); // constexpr in C++14 30 template <class... U> 31 tuple(tuple<U...>&&); // constexpr in C++14 32 template <class U1, class U2> 33 tuple(const pair<U1, U2>&); // iff sizeof...(T) == 2 // constexpr in C++14 34 template <class U1, class U2> 35 tuple(pair<U1, U2>&&); // iff sizeof...(T) == 2 // constexpr in C++14 36 37 // allocator-extended constructors 38 template <class Alloc> 39 tuple(allocator_arg_t, const Alloc& a); 40 template <class Alloc> 41 tuple(allocator_arg_t, const Alloc& a, const T&...); 42 template <class Alloc, class... U> 43 tuple(allocator_arg_t, const Alloc& a, U&&...); 44 template <class Alloc> 45 tuple(allocator_arg_t, const Alloc& a, const tuple&); 46 template <class Alloc> 47 tuple(allocator_arg_t, const Alloc& a, tuple&&); 48 template <class Alloc, class... U> 49 tuple(allocator_arg_t, const Alloc& a, const tuple<U...>&); 50 template <class Alloc, class... U> 51 tuple(allocator_arg_t, const Alloc& a, tuple<U...>&&); 52 template <class Alloc, class U1, class U2> 53 tuple(allocator_arg_t, const Alloc& a, const pair<U1, U2>&); 54 template <class Alloc, class U1, class U2> 55 tuple(allocator_arg_t, const Alloc& a, pair<U1, U2>&&); 56 57 tuple& operator=(const tuple&); 58 tuple& 59 operator=(tuple&&) noexcept(AND(is_nothrow_move_assignable<T>::value ...)); 60 template <class... U> 61 tuple& operator=(const tuple<U...>&); 62 template <class... U> 63 tuple& operator=(tuple<U...>&&); 64 template <class U1, class U2> 65 tuple& operator=(const pair<U1, U2>&); // iff sizeof...(T) == 2 66 template <class U1, class U2> 67 tuple& operator=(pair<U1, U2>&&); // iff sizeof...(T) == 2 68 69 void swap(tuple&) noexcept(AND(swap(declval<T&>(), declval<T&>())...)); 70}; 71 72inline constexpr unspecified ignore; 73 74template <class... T> tuple<V...> make_tuple(T&&...); // constexpr in C++14 75template <class... T> tuple<ATypes...> forward_as_tuple(T&&...) noexcept; // constexpr in C++14 76template <class... T> tuple<T&...> tie(T&...) noexcept; // constexpr in C++14 77template <class... Tuples> tuple<CTypes...> tuple_cat(Tuples&&... tpls); // constexpr in C++14 78 79// [tuple.apply], calling a function with a tuple of arguments: 80template <class F, class Tuple> 81 constexpr decltype(auto) apply(F&& f, Tuple&& t); // C++17 82template <class T, class Tuple> 83 constexpr T make_from_tuple(Tuple&& t); // C++17 84 85// 20.4.1.4, tuple helper classes: 86template <class T> struct tuple_size; // undefined 87template <class... T> struct tuple_size<tuple<T...>>; 88template <class T> 89 inline constexpr size_t tuple_size_v = tuple_size<T>::value; // C++17 90template <size_t I, class T> struct tuple_element; // undefined 91template <size_t I, class... T> struct tuple_element<I, tuple<T...>>; 92template <size_t I, class T> 93 using tuple_element_t = typename tuple_element <I, T>::type; // C++14 94 95// 20.4.1.5, element access: 96template <size_t I, class... T> 97 typename tuple_element<I, tuple<T...>>::type& 98 get(tuple<T...>&) noexcept; // constexpr in C++14 99template <size_t I, class... T> 100 const typename tuple_element<I, tuple<T...>>::type& 101 get(const tuple<T...>&) noexcept; // constexpr in C++14 102template <size_t I, class... T> 103 typename tuple_element<I, tuple<T...>>::type&& 104 get(tuple<T...>&&) noexcept; // constexpr in C++14 105template <size_t I, class... T> 106 const typename tuple_element<I, tuple<T...>>::type&& 107 get(const tuple<T...>&&) noexcept; // constexpr in C++14 108 109template <class T1, class... T> 110 constexpr T1& get(tuple<T...>&) noexcept; // C++14 111template <class T1, class... T> 112 constexpr const T1& get(const tuple<T...>&) noexcept; // C++14 113template <class T1, class... T> 114 constexpr T1&& get(tuple<T...>&&) noexcept; // C++14 115template <class T1, class... T> 116 constexpr const T1&& get(const tuple<T...>&&) noexcept; // C++14 117 118// 20.4.1.6, relational operators: 119template<class... T, class... U> bool operator==(const tuple<T...>&, const tuple<U...>&); // constexpr in C++14 120template<class... T, class... U> bool operator<(const tuple<T...>&, const tuple<U...>&); // constexpr in C++14 121template<class... T, class... U> bool operator!=(const tuple<T...>&, const tuple<U...>&); // constexpr in C++14 122template<class... T, class... U> bool operator>(const tuple<T...>&, const tuple<U...>&); // constexpr in C++14 123template<class... T, class... U> bool operator<=(const tuple<T...>&, const tuple<U...>&); // constexpr in C++14 124template<class... T, class... U> bool operator>=(const tuple<T...>&, const tuple<U...>&); // constexpr in C++14 125 126template <class... Types, class Alloc> 127 struct uses_allocator<tuple<Types...>, Alloc>; 128 129template <class... Types> 130 void 131 swap(tuple<Types...>& x, tuple<Types...>& y) noexcept(noexcept(x.swap(y))); 132 133} // std 134 135*/ 136 137#include <__config> 138#include <__tuple> 139#include <cstddef> 140#include <type_traits> 141#include <__functional_base> 142#include <utility> 143#include <version> 144 145#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 146#pragma GCC system_header 147#endif 148 149_LIBCPP_BEGIN_NAMESPACE_STD 150 151#ifndef _LIBCPP_CXX03_LANG 152 153 154// __tuple_leaf 155 156template <size_t _Ip, class _Hp, 157 bool=is_empty<_Hp>::value && !__libcpp_is_final<_Hp>::value 158 > 159class __tuple_leaf; 160 161template <size_t _Ip, class _Hp, bool _Ep> 162inline _LIBCPP_INLINE_VISIBILITY 163void swap(__tuple_leaf<_Ip, _Hp, _Ep>& __x, __tuple_leaf<_Ip, _Hp, _Ep>& __y) 164 _NOEXCEPT_(__is_nothrow_swappable<_Hp>::value) 165{ 166 swap(__x.get(), __y.get()); 167} 168 169template <size_t _Ip, class _Hp, bool> 170class __tuple_leaf 171{ 172 _Hp __value_; 173 174 template <class _Tp> 175 static constexpr bool __can_bind_reference() { 176#if __has_keyword(__reference_binds_to_temporary) 177 return !__reference_binds_to_temporary(_Hp, _Tp); 178#else 179 return true; 180#endif 181 } 182 183 __tuple_leaf& operator=(const __tuple_leaf&); 184public: 185 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR __tuple_leaf() 186 _NOEXCEPT_(is_nothrow_default_constructible<_Hp>::value) : __value_() 187 {static_assert(!is_reference<_Hp>::value, 188 "Attempted to default construct a reference element in a tuple");} 189 190 template <class _Alloc> 191 _LIBCPP_INLINE_VISIBILITY 192 __tuple_leaf(integral_constant<int, 0>, const _Alloc&) 193 : __value_() 194 {static_assert(!is_reference<_Hp>::value, 195 "Attempted to default construct a reference element in a tuple");} 196 197 template <class _Alloc> 198 _LIBCPP_INLINE_VISIBILITY 199 __tuple_leaf(integral_constant<int, 1>, const _Alloc& __a) 200 : __value_(allocator_arg_t(), __a) 201 {static_assert(!is_reference<_Hp>::value, 202 "Attempted to default construct a reference element in a tuple");} 203 204 template <class _Alloc> 205 _LIBCPP_INLINE_VISIBILITY 206 __tuple_leaf(integral_constant<int, 2>, const _Alloc& __a) 207 : __value_(__a) 208 {static_assert(!is_reference<_Hp>::value, 209 "Attempted to default construct a reference element in a tuple");} 210 211 template <class _Tp, 212 class = _EnableIf< 213 _And< 214 _IsNotSame<__uncvref_t<_Tp>, __tuple_leaf>, 215 is_constructible<_Hp, _Tp> 216 >::value 217 > 218 > 219 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 220 explicit __tuple_leaf(_Tp&& __t) _NOEXCEPT_((is_nothrow_constructible<_Hp, _Tp>::value)) 221 : __value_(_VSTD::forward<_Tp>(__t)) 222 {static_assert(__can_bind_reference<_Tp&&>(), 223 "Attempted construction of reference element binds to a temporary whose lifetime has ended");} 224 225 template <class _Tp, class _Alloc> 226 _LIBCPP_INLINE_VISIBILITY 227 explicit __tuple_leaf(integral_constant<int, 0>, const _Alloc&, _Tp&& __t) 228 : __value_(_VSTD::forward<_Tp>(__t)) 229 {static_assert(__can_bind_reference<_Tp&&>(), 230 "Attempted construction of reference element binds to a temporary whose lifetime has ended");} 231 232 template <class _Tp, class _Alloc> 233 _LIBCPP_INLINE_VISIBILITY 234 explicit __tuple_leaf(integral_constant<int, 1>, const _Alloc& __a, _Tp&& __t) 235 : __value_(allocator_arg_t(), __a, _VSTD::forward<_Tp>(__t)) 236 {static_assert(!is_reference<_Hp>::value, 237 "Attempted to uses-allocator construct a reference element in a tuple");} 238 239 template <class _Tp, class _Alloc> 240 _LIBCPP_INLINE_VISIBILITY 241 explicit __tuple_leaf(integral_constant<int, 2>, const _Alloc& __a, _Tp&& __t) 242 : __value_(_VSTD::forward<_Tp>(__t), __a) 243 {static_assert(!is_reference<_Hp>::value, 244 "Attempted to uses-allocator construct a reference element in a tuple");} 245 246 __tuple_leaf(const __tuple_leaf& __t) = default; 247 __tuple_leaf(__tuple_leaf&& __t) = default; 248 249 template <class _Tp> 250 _LIBCPP_INLINE_VISIBILITY 251 __tuple_leaf& 252 operator=(_Tp&& __t) _NOEXCEPT_((is_nothrow_assignable<_Hp&, _Tp>::value)) 253 { 254 __value_ = _VSTD::forward<_Tp>(__t); 255 return *this; 256 } 257 258 _LIBCPP_INLINE_VISIBILITY 259 int swap(__tuple_leaf& __t) _NOEXCEPT_(__is_nothrow_swappable<__tuple_leaf>::value) 260 { 261 _VSTD::swap(*this, __t); 262 return 0; 263 } 264 265 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 _Hp& get() _NOEXCEPT {return __value_;} 266 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 const _Hp& get() const _NOEXCEPT {return __value_;} 267}; 268 269template <size_t _Ip, class _Hp> 270class __tuple_leaf<_Ip, _Hp, true> 271 : private _Hp 272{ 273 274 __tuple_leaf& operator=(const __tuple_leaf&); 275public: 276 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR __tuple_leaf() 277 _NOEXCEPT_(is_nothrow_default_constructible<_Hp>::value) {} 278 279 template <class _Alloc> 280 _LIBCPP_INLINE_VISIBILITY 281 __tuple_leaf(integral_constant<int, 0>, const _Alloc&) {} 282 283 template <class _Alloc> 284 _LIBCPP_INLINE_VISIBILITY 285 __tuple_leaf(integral_constant<int, 1>, const _Alloc& __a) 286 : _Hp(allocator_arg_t(), __a) {} 287 288 template <class _Alloc> 289 _LIBCPP_INLINE_VISIBILITY 290 __tuple_leaf(integral_constant<int, 2>, const _Alloc& __a) 291 : _Hp(__a) {} 292 293 template <class _Tp, 294 class = _EnableIf< 295 _And< 296 _IsNotSame<__uncvref_t<_Tp>, __tuple_leaf>, 297 is_constructible<_Hp, _Tp> 298 >::value 299 > 300 > 301 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 302 explicit __tuple_leaf(_Tp&& __t) _NOEXCEPT_((is_nothrow_constructible<_Hp, _Tp>::value)) 303 : _Hp(_VSTD::forward<_Tp>(__t)) {} 304 305 template <class _Tp, class _Alloc> 306 _LIBCPP_INLINE_VISIBILITY 307 explicit __tuple_leaf(integral_constant<int, 0>, const _Alloc&, _Tp&& __t) 308 : _Hp(_VSTD::forward<_Tp>(__t)) {} 309 310 template <class _Tp, class _Alloc> 311 _LIBCPP_INLINE_VISIBILITY 312 explicit __tuple_leaf(integral_constant<int, 1>, const _Alloc& __a, _Tp&& __t) 313 : _Hp(allocator_arg_t(), __a, _VSTD::forward<_Tp>(__t)) {} 314 315 template <class _Tp, class _Alloc> 316 _LIBCPP_INLINE_VISIBILITY 317 explicit __tuple_leaf(integral_constant<int, 2>, const _Alloc& __a, _Tp&& __t) 318 : _Hp(_VSTD::forward<_Tp>(__t), __a) {} 319 320 __tuple_leaf(__tuple_leaf const &) = default; 321 __tuple_leaf(__tuple_leaf &&) = default; 322 323 template <class _Tp> 324 _LIBCPP_INLINE_VISIBILITY 325 __tuple_leaf& 326 operator=(_Tp&& __t) _NOEXCEPT_((is_nothrow_assignable<_Hp&, _Tp>::value)) 327 { 328 _Hp::operator=(_VSTD::forward<_Tp>(__t)); 329 return *this; 330 } 331 332 _LIBCPP_INLINE_VISIBILITY 333 int 334 swap(__tuple_leaf& __t) _NOEXCEPT_(__is_nothrow_swappable<__tuple_leaf>::value) 335 { 336 _VSTD::swap(*this, __t); 337 return 0; 338 } 339 340 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 _Hp& get() _NOEXCEPT {return static_cast<_Hp&>(*this);} 341 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 const _Hp& get() const _NOEXCEPT {return static_cast<const _Hp&>(*this);} 342}; 343 344template <class ..._Tp> 345_LIBCPP_INLINE_VISIBILITY 346void __swallow(_Tp&&...) _NOEXCEPT {} 347 348template <class _Tp> 349struct __all_default_constructible; 350 351template <class ..._Tp> 352struct __all_default_constructible<__tuple_types<_Tp...>> 353 : __all<is_default_constructible<_Tp>::value...> 354{ }; 355 356// __tuple_impl 357 358template<class _Indx, class ..._Tp> struct __tuple_impl; 359 360template<size_t ..._Indx, class ..._Tp> 361struct _LIBCPP_DECLSPEC_EMPTY_BASES __tuple_impl<__tuple_indices<_Indx...>, _Tp...> 362 : public __tuple_leaf<_Indx, _Tp>... 363{ 364 _LIBCPP_INLINE_VISIBILITY 365 _LIBCPP_CONSTEXPR __tuple_impl() 366 _NOEXCEPT_(__all<is_nothrow_default_constructible<_Tp>::value...>::value) {} 367 368 template <size_t ..._Uf, class ..._Tf, 369 size_t ..._Ul, class ..._Tl, class ..._Up> 370 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 371 explicit 372 __tuple_impl(__tuple_indices<_Uf...>, __tuple_types<_Tf...>, 373 __tuple_indices<_Ul...>, __tuple_types<_Tl...>, 374 _Up&&... __u) 375 _NOEXCEPT_((__all<is_nothrow_constructible<_Tf, _Up>::value...>::value && 376 __all<is_nothrow_default_constructible<_Tl>::value...>::value)) : 377 __tuple_leaf<_Uf, _Tf>(_VSTD::forward<_Up>(__u))..., 378 __tuple_leaf<_Ul, _Tl>()... 379 {} 380 381 template <class _Alloc, size_t ..._Uf, class ..._Tf, 382 size_t ..._Ul, class ..._Tl, class ..._Up> 383 _LIBCPP_INLINE_VISIBILITY 384 explicit 385 __tuple_impl(allocator_arg_t, const _Alloc& __a, 386 __tuple_indices<_Uf...>, __tuple_types<_Tf...>, 387 __tuple_indices<_Ul...>, __tuple_types<_Tl...>, 388 _Up&&... __u) : 389 __tuple_leaf<_Uf, _Tf>(__uses_alloc_ctor<_Tf, _Alloc, _Up>(), __a, 390 _VSTD::forward<_Up>(__u))..., 391 __tuple_leaf<_Ul, _Tl>(__uses_alloc_ctor<_Tl, _Alloc>(), __a)... 392 {} 393 394 template <class _Tuple, 395 class = typename enable_if 396 < 397 __tuple_constructible<_Tuple, tuple<_Tp...> >::value 398 >::type 399 > 400 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 401 __tuple_impl(_Tuple&& __t) _NOEXCEPT_((__all<is_nothrow_constructible<_Tp, typename tuple_element<_Indx, 402 typename __make_tuple_types<_Tuple>::type>::type>::value...>::value)) 403 : __tuple_leaf<_Indx, _Tp>(_VSTD::forward<typename tuple_element<_Indx, 404 typename __make_tuple_types<_Tuple>::type>::type>(_VSTD::get<_Indx>(__t)))... 405 {} 406 407 template <class _Alloc, class _Tuple, 408 class = typename enable_if 409 < 410 __tuple_constructible<_Tuple, tuple<_Tp...> >::value 411 >::type 412 > 413 _LIBCPP_INLINE_VISIBILITY 414 __tuple_impl(allocator_arg_t, const _Alloc& __a, _Tuple&& __t) 415 : __tuple_leaf<_Indx, _Tp>(__uses_alloc_ctor<_Tp, _Alloc, typename tuple_element<_Indx, 416 typename __make_tuple_types<_Tuple>::type>::type>(), __a, 417 _VSTD::forward<typename tuple_element<_Indx, 418 typename __make_tuple_types<_Tuple>::type>::type>(_VSTD::get<_Indx>(__t)))... 419 {} 420 421 template <class _Tuple> 422 _LIBCPP_INLINE_VISIBILITY 423 typename enable_if 424 < 425 __tuple_assignable<_Tuple, tuple<_Tp...> >::value, 426 __tuple_impl& 427 >::type 428 operator=(_Tuple&& __t) _NOEXCEPT_((__all<is_nothrow_assignable<_Tp&, typename tuple_element<_Indx, 429 typename __make_tuple_types<_Tuple>::type>::type>::value...>::value)) 430 { 431 __swallow(__tuple_leaf<_Indx, _Tp>::operator=(_VSTD::forward<typename tuple_element<_Indx, 432 typename __make_tuple_types<_Tuple>::type>::type>(_VSTD::get<_Indx>(__t)))...); 433 return *this; 434 } 435 436 __tuple_impl(const __tuple_impl&) = default; 437 __tuple_impl(__tuple_impl&&) = default; 438 439 _LIBCPP_INLINE_VISIBILITY 440 __tuple_impl& 441 operator=(const __tuple_impl& __t) _NOEXCEPT_((__all<is_nothrow_copy_assignable<_Tp>::value...>::value)) 442 { 443 __swallow(__tuple_leaf<_Indx, _Tp>::operator=(static_cast<const __tuple_leaf<_Indx, _Tp>&>(__t).get())...); 444 return *this; 445 } 446 447 _LIBCPP_INLINE_VISIBILITY 448 __tuple_impl& 449 operator=(__tuple_impl&& __t) _NOEXCEPT_((__all<is_nothrow_move_assignable<_Tp>::value...>::value)) 450 { 451 __swallow(__tuple_leaf<_Indx, _Tp>::operator=(_VSTD::forward<_Tp>(static_cast<__tuple_leaf<_Indx, _Tp>&>(__t).get()))...); 452 return *this; 453 } 454 455 _LIBCPP_INLINE_VISIBILITY 456 void swap(__tuple_impl& __t) 457 _NOEXCEPT_(__all<__is_nothrow_swappable<_Tp>::value...>::value) 458 { 459 __swallow(__tuple_leaf<_Indx, _Tp>::swap(static_cast<__tuple_leaf<_Indx, _Tp>&>(__t))...); 460 } 461}; 462 463 464 465template <class ..._Tp> 466class _LIBCPP_TEMPLATE_VIS tuple 467{ 468 typedef __tuple_impl<typename __make_tuple_indices<sizeof...(_Tp)>::type, _Tp...> _BaseT; 469 470 _BaseT __base_; 471 472#if defined(_LIBCPP_ENABLE_TUPLE_IMPLICIT_REDUCED_ARITY_EXTENSION) 473 static constexpr bool _EnableImplicitReducedArityExtension = true; 474#else 475 static constexpr bool _EnableImplicitReducedArityExtension = false; 476#endif 477 478 template <class ..._Args> 479 struct _PackExpandsToThisTuple : false_type {}; 480 481 template <class _Arg> 482 struct _PackExpandsToThisTuple<_Arg> 483 : is_same<typename __uncvref<_Arg>::type, tuple> {}; 484 485 template <bool _MaybeEnable, class _Dummy = void> 486 struct _CheckArgsConstructor : __check_tuple_constructor_fail {}; 487 488 template <class _Dummy> 489 struct _CheckArgsConstructor<true, _Dummy> 490 { 491 template <class ..._Args> 492 static constexpr bool __enable_default() { 493 return __all<is_default_constructible<_Args>::value...>::value; 494 } 495 496 template <class ..._Args> 497 static constexpr bool __enable_explicit() { 498 return 499 __tuple_constructible< 500 tuple<_Args...>, 501 typename __make_tuple_types<tuple, 502 sizeof...(_Args) < sizeof...(_Tp) ? 503 sizeof...(_Args) : 504 sizeof...(_Tp)>::type 505 >::value && 506 !__tuple_convertible< 507 tuple<_Args...>, 508 typename __make_tuple_types<tuple, 509 sizeof...(_Args) < sizeof...(_Tp) ? 510 sizeof...(_Args) : 511 sizeof...(_Tp)>::type 512 >::value && 513 __all_default_constructible< 514 typename __make_tuple_types<tuple, sizeof...(_Tp), 515 sizeof...(_Args) < sizeof...(_Tp) ? 516 sizeof...(_Args) : 517 sizeof...(_Tp)>::type 518 >::value; 519 } 520 521 template <class ..._Args> 522 static constexpr bool __enable_implicit() { 523 return 524 __tuple_constructible< 525 tuple<_Args...>, 526 typename __make_tuple_types<tuple, 527 sizeof...(_Args) < sizeof...(_Tp) ? 528 sizeof...(_Args) : 529 sizeof...(_Tp)>::type 530 >::value && 531 __tuple_convertible< 532 tuple<_Args...>, 533 typename __make_tuple_types<tuple, 534 sizeof...(_Args) < sizeof...(_Tp) ? 535 sizeof...(_Args) : 536 sizeof...(_Tp)>::type 537 >::value && 538 __all_default_constructible< 539 typename __make_tuple_types<tuple, sizeof...(_Tp), 540 sizeof...(_Args) < sizeof...(_Tp) ? 541 sizeof...(_Args) : 542 sizeof...(_Tp)>::type 543 >::value; 544 } 545 }; 546 547 template <bool _MaybeEnable, 548 bool = sizeof...(_Tp) == 1, 549 class _Dummy = void> 550 struct _CheckTupleLikeConstructor : __check_tuple_constructor_fail {}; 551 552 template <class _Dummy> 553 struct _CheckTupleLikeConstructor<true, false, _Dummy> 554 { 555 template <class _Tuple> 556 static constexpr bool __enable_implicit() { 557 return __tuple_constructible<_Tuple, tuple>::value 558 && __tuple_convertible<_Tuple, tuple>::value; 559 } 560 561 template <class _Tuple> 562 static constexpr bool __enable_explicit() { 563 return __tuple_constructible<_Tuple, tuple>::value 564 && !__tuple_convertible<_Tuple, tuple>::value; 565 } 566 }; 567 568 template <class _Dummy> 569 struct _CheckTupleLikeConstructor<true, true, _Dummy> 570 { 571 // This trait is used to disable the tuple-like constructor when 572 // the UTypes... constructor should be selected instead. 573 // See LWG issue #2549. 574 template <class _Tuple> 575 using _PreferTupleLikeConstructor = _Or< 576 // Don't attempt the two checks below if the tuple we are given 577 // has the same type as this tuple. 578 _IsSame<__uncvref_t<_Tuple>, tuple>, 579 _Lazy<_And, 580 _Not<is_constructible<_Tp..., _Tuple>>, 581 _Not<is_convertible<_Tuple, _Tp...>> 582 > 583 >; 584 585 template <class _Tuple> 586 static constexpr bool __enable_implicit() { 587 return _And< 588 __tuple_constructible<_Tuple, tuple>, 589 __tuple_convertible<_Tuple, tuple>, 590 _PreferTupleLikeConstructor<_Tuple> 591 >::value; 592 } 593 594 template <class _Tuple> 595 static constexpr bool __enable_explicit() { 596 return _And< 597 __tuple_constructible<_Tuple, tuple>, 598 _PreferTupleLikeConstructor<_Tuple>, 599 _Not<__tuple_convertible<_Tuple, tuple>> 600 >::value; 601 } 602 }; 603 604 template <class _Tuple, bool _DisableIfLValue> 605 using _EnableImplicitTupleLikeConstructor = _EnableIf< 606 _CheckTupleLikeConstructor< 607 __tuple_like_with_size<_Tuple, sizeof...(_Tp)>::value 608 && !_PackExpandsToThisTuple<_Tuple>::value 609 && (!is_lvalue_reference<_Tuple>::value || !_DisableIfLValue) 610 >::template __enable_implicit<_Tuple>(), 611 bool 612 >; 613 614 template <class _Tuple, bool _DisableIfLValue> 615 using _EnableExplicitTupleLikeConstructor = _EnableIf< 616 _CheckTupleLikeConstructor< 617 __tuple_like_with_size<_Tuple, sizeof...(_Tp)>::value 618 && !_PackExpandsToThisTuple<_Tuple>::value 619 && (!is_lvalue_reference<_Tuple>::value || !_DisableIfLValue) 620 >::template __enable_explicit<_Tuple>(), 621 bool 622 >; 623 template <size_t _Jp, class ..._Up> friend _LIBCPP_CONSTEXPR_AFTER_CXX11 624 typename tuple_element<_Jp, tuple<_Up...> >::type& get(tuple<_Up...>&) _NOEXCEPT; 625 template <size_t _Jp, class ..._Up> friend _LIBCPP_CONSTEXPR_AFTER_CXX11 626 const typename tuple_element<_Jp, tuple<_Up...> >::type& get(const tuple<_Up...>&) _NOEXCEPT; 627 template <size_t _Jp, class ..._Up> friend _LIBCPP_CONSTEXPR_AFTER_CXX11 628 typename tuple_element<_Jp, tuple<_Up...> >::type&& get(tuple<_Up...>&&) _NOEXCEPT; 629 template <size_t _Jp, class ..._Up> friend _LIBCPP_CONSTEXPR_AFTER_CXX11 630 const typename tuple_element<_Jp, tuple<_Up...> >::type&& get(const tuple<_Up...>&&) _NOEXCEPT; 631public: 632 633 template <bool _Dummy = true, class = typename enable_if< 634 _CheckArgsConstructor<_Dummy>::template __enable_default<_Tp...>() 635 >::type> 636 _LIBCPP_INLINE_VISIBILITY 637 _LIBCPP_CONSTEXPR tuple() 638 _NOEXCEPT_(__all<is_nothrow_default_constructible<_Tp>::value...>::value) {} 639 640 tuple(tuple const&) = default; 641 tuple(tuple&&) = default; 642 643 template <class _AllocArgT, class _Alloc, bool _Dummy = true, class = _EnableIf< 644 _And< 645 _IsSame<allocator_arg_t, _AllocArgT>, 646 __dependent_type<is_default_constructible<_Tp>, _Dummy>... 647 >::value 648 > 649 > 650 _LIBCPP_INLINE_VISIBILITY 651 tuple(_AllocArgT, _Alloc const& __a) 652 : __base_(allocator_arg_t(), __a, 653 __tuple_indices<>(), __tuple_types<>(), 654 typename __make_tuple_indices<sizeof...(_Tp), 0>::type(), 655 __tuple_types<_Tp...>()) {} 656 657 template <bool _Dummy = true, 658 typename enable_if 659 < 660 _CheckArgsConstructor< 661 _Dummy 662 >::template __enable_implicit<_Tp const&...>(), 663 bool 664 >::type = false 665 > 666 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 667 tuple(const _Tp& ... __t) _NOEXCEPT_((__all<is_nothrow_copy_constructible<_Tp>::value...>::value)) 668 : __base_(typename __make_tuple_indices<sizeof...(_Tp)>::type(), 669 typename __make_tuple_types<tuple, sizeof...(_Tp)>::type(), 670 typename __make_tuple_indices<0>::type(), 671 typename __make_tuple_types<tuple, 0>::type(), 672 __t... 673 ) {} 674 675 template <bool _Dummy = true, 676 typename enable_if 677 < 678 _CheckArgsConstructor< 679 _Dummy 680 >::template __enable_explicit<_Tp const&...>(), 681 bool 682 >::type = false 683 > 684 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 685 explicit tuple(const _Tp& ... __t) _NOEXCEPT_((__all<is_nothrow_copy_constructible<_Tp>::value...>::value)) 686 : __base_(typename __make_tuple_indices<sizeof...(_Tp)>::type(), 687 typename __make_tuple_types<tuple, sizeof...(_Tp)>::type(), 688 typename __make_tuple_indices<0>::type(), 689 typename __make_tuple_types<tuple, 0>::type(), 690 __t... 691 ) {} 692 693 template <class _Alloc, bool _Dummy = true, 694 typename enable_if 695 < 696 _CheckArgsConstructor< 697 _Dummy 698 >::template __enable_implicit<_Tp const&...>(), 699 bool 700 >::type = false 701 > 702 _LIBCPP_INLINE_VISIBILITY 703 tuple(allocator_arg_t, const _Alloc& __a, const _Tp& ... __t) 704 : __base_(allocator_arg_t(), __a, 705 typename __make_tuple_indices<sizeof...(_Tp)>::type(), 706 typename __make_tuple_types<tuple, sizeof...(_Tp)>::type(), 707 typename __make_tuple_indices<0>::type(), 708 typename __make_tuple_types<tuple, 0>::type(), 709 __t... 710 ) {} 711 712 template <class _Alloc, bool _Dummy = true, 713 typename enable_if 714 < 715 _CheckArgsConstructor< 716 _Dummy 717 >::template __enable_explicit<_Tp const&...>(), 718 bool 719 >::type = false 720 > 721 _LIBCPP_INLINE_VISIBILITY 722 explicit 723 tuple(allocator_arg_t, const _Alloc& __a, const _Tp& ... __t) 724 : __base_(allocator_arg_t(), __a, 725 typename __make_tuple_indices<sizeof...(_Tp)>::type(), 726 typename __make_tuple_types<tuple, sizeof...(_Tp)>::type(), 727 typename __make_tuple_indices<0>::type(), 728 typename __make_tuple_types<tuple, 0>::type(), 729 __t... 730 ) {} 731 732 template <class ..._Up, 733 bool _PackIsTuple = _PackExpandsToThisTuple<_Up...>::value, 734 typename enable_if 735 < 736 _CheckArgsConstructor< 737 sizeof...(_Up) == sizeof...(_Tp) 738 && !_PackIsTuple 739 >::template __enable_implicit<_Up...>() || 740 _CheckArgsConstructor< 741 _EnableImplicitReducedArityExtension 742 && sizeof...(_Up) < sizeof...(_Tp) 743 && !_PackIsTuple 744 >::template __enable_implicit<_Up...>(), 745 bool 746 >::type = false 747 > 748 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 749 tuple(_Up&&... __u) 750 _NOEXCEPT_(( 751 is_nothrow_constructible<_BaseT, 752 typename __make_tuple_indices<sizeof...(_Up)>::type, 753 typename __make_tuple_types<tuple, sizeof...(_Up)>::type, 754 typename __make_tuple_indices<sizeof...(_Tp), sizeof...(_Up)>::type, 755 typename __make_tuple_types<tuple, sizeof...(_Tp), sizeof...(_Up)>::type, 756 _Up... 757 >::value 758 )) 759 : __base_(typename __make_tuple_indices<sizeof...(_Up)>::type(), 760 typename __make_tuple_types<tuple, sizeof...(_Up)>::type(), 761 typename __make_tuple_indices<sizeof...(_Tp), sizeof...(_Up)>::type(), 762 typename __make_tuple_types<tuple, sizeof...(_Tp), sizeof...(_Up)>::type(), 763 _VSTD::forward<_Up>(__u)...) {} 764 765 template <class ..._Up, 766 typename enable_if 767 < 768 _CheckArgsConstructor< 769 sizeof...(_Up) <= sizeof...(_Tp) 770 && !_PackExpandsToThisTuple<_Up...>::value 771 >::template __enable_explicit<_Up...>() || 772 _CheckArgsConstructor< 773 !_EnableImplicitReducedArityExtension 774 && sizeof...(_Up) < sizeof...(_Tp) 775 && !_PackExpandsToThisTuple<_Up...>::value 776 >::template __enable_implicit<_Up...>(), 777 bool 778 >::type = false 779 > 780 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 781 explicit 782 tuple(_Up&&... __u) 783 _NOEXCEPT_(( 784 is_nothrow_constructible<_BaseT, 785 typename __make_tuple_indices<sizeof...(_Up)>::type, 786 typename __make_tuple_types<tuple, sizeof...(_Up)>::type, 787 typename __make_tuple_indices<sizeof...(_Tp), sizeof...(_Up)>::type, 788 typename __make_tuple_types<tuple, sizeof...(_Tp), sizeof...(_Up)>::type, 789 _Up... 790 >::value 791 )) 792 : __base_(typename __make_tuple_indices<sizeof...(_Up)>::type(), 793 typename __make_tuple_types<tuple, sizeof...(_Up)>::type(), 794 typename __make_tuple_indices<sizeof...(_Tp), sizeof...(_Up)>::type(), 795 typename __make_tuple_types<tuple, sizeof...(_Tp), sizeof...(_Up)>::type(), 796 _VSTD::forward<_Up>(__u)...) {} 797 798 template <class _Alloc, class ..._Up, 799 typename enable_if 800 < 801 _CheckArgsConstructor< 802 sizeof...(_Up) == sizeof...(_Tp) && 803 !_PackExpandsToThisTuple<_Up...>::value 804 >::template __enable_implicit<_Up...>(), 805 bool 806 >::type = false 807 > 808 _LIBCPP_INLINE_VISIBILITY 809 tuple(allocator_arg_t, const _Alloc& __a, _Up&&... __u) 810 : __base_(allocator_arg_t(), __a, 811 typename __make_tuple_indices<sizeof...(_Up)>::type(), 812 typename __make_tuple_types<tuple, sizeof...(_Up)>::type(), 813 typename __make_tuple_indices<sizeof...(_Tp), sizeof...(_Up)>::type(), 814 typename __make_tuple_types<tuple, sizeof...(_Tp), sizeof...(_Up)>::type(), 815 _VSTD::forward<_Up>(__u)...) {} 816 817 template <class _Alloc, class ..._Up, 818 typename enable_if 819 < 820 _CheckArgsConstructor< 821 sizeof...(_Up) == sizeof...(_Tp) && 822 !_PackExpandsToThisTuple<_Up...>::value 823 >::template __enable_explicit<_Up...>(), 824 bool 825 >::type = false 826 > 827 _LIBCPP_INLINE_VISIBILITY 828 explicit 829 tuple(allocator_arg_t, const _Alloc& __a, _Up&&... __u) 830 : __base_(allocator_arg_t(), __a, 831 typename __make_tuple_indices<sizeof...(_Up)>::type(), 832 typename __make_tuple_types<tuple, sizeof...(_Up)>::type(), 833 typename __make_tuple_indices<sizeof...(_Tp), sizeof...(_Up)>::type(), 834 typename __make_tuple_types<tuple, sizeof...(_Tp), sizeof...(_Up)>::type(), 835 _VSTD::forward<_Up>(__u)...) {} 836 837 template <class _Tuple, _EnableImplicitTupleLikeConstructor<_Tuple, true> = false> 838 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 839 tuple(_Tuple&& __t) _NOEXCEPT_((is_nothrow_constructible<_BaseT, _Tuple>::value)) 840 : __base_(_VSTD::forward<_Tuple>(__t)) {} 841 842 template <class _Tuple, _EnableImplicitTupleLikeConstructor<const _Tuple&, false> = false> 843 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 844 tuple(const _Tuple& __t) _NOEXCEPT_((is_nothrow_constructible<_BaseT, const _Tuple&>::value)) 845 : __base_(__t) {} 846 template <class _Tuple, _EnableExplicitTupleLikeConstructor<_Tuple, true> = false> 847 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 848 explicit 849 tuple(_Tuple&& __t) _NOEXCEPT_((is_nothrow_constructible<_BaseT, _Tuple>::value)) 850 : __base_(_VSTD::forward<_Tuple>(__t)) {} 851 852 template <class _Tuple, _EnableExplicitTupleLikeConstructor<const _Tuple&, false> = false> 853 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 854 explicit 855 tuple(const _Tuple& __t) _NOEXCEPT_((is_nothrow_constructible<_BaseT, const _Tuple&>::value)) 856 : __base_(__t) {} 857 858 template <class _Alloc, class _Tuple, 859 typename enable_if 860 < 861 _CheckTupleLikeConstructor< 862 __tuple_like_with_size<_Tuple, sizeof...(_Tp)>::value 863 >::template __enable_implicit<_Tuple>(), 864 bool 865 >::type = false 866 > 867 _LIBCPP_INLINE_VISIBILITY 868 tuple(allocator_arg_t, const _Alloc& __a, _Tuple&& __t) 869 : __base_(allocator_arg_t(), __a, _VSTD::forward<_Tuple>(__t)) {} 870 871 template <class _Alloc, class _Tuple, 872 typename enable_if 873 < 874 _CheckTupleLikeConstructor< 875 __tuple_like_with_size<_Tuple, sizeof...(_Tp)>::value 876 >::template __enable_explicit<_Tuple>(), 877 bool 878 >::type = false 879 > 880 _LIBCPP_INLINE_VISIBILITY 881 explicit 882 tuple(allocator_arg_t, const _Alloc& __a, _Tuple&& __t) 883 : __base_(allocator_arg_t(), __a, _VSTD::forward<_Tuple>(__t)) {} 884 885 using _CanCopyAssign = __all<is_copy_assignable<_Tp>::value...>; 886 using _CanMoveAssign = __all<is_move_assignable<_Tp>::value...>; 887 888 _LIBCPP_INLINE_VISIBILITY 889 tuple& operator=(typename conditional<_CanCopyAssign::value, tuple, __nat>::type const& __t) 890 _NOEXCEPT_((__all<is_nothrow_copy_assignable<_Tp>::value...>::value)) 891 { 892 __base_.operator=(__t.__base_); 893 return *this; 894 } 895 896 _LIBCPP_INLINE_VISIBILITY 897 tuple& operator=(typename conditional<_CanMoveAssign::value, tuple, __nat>::type&& __t) 898 _NOEXCEPT_((__all<is_nothrow_move_assignable<_Tp>::value...>::value)) 899 { 900 __base_.operator=(static_cast<_BaseT&&>(__t.__base_)); 901 return *this; 902 } 903 904 template <class _Tuple, 905 class = typename enable_if 906 < 907 __tuple_assignable<_Tuple, tuple>::value 908 >::type 909 > 910 _LIBCPP_INLINE_VISIBILITY 911 tuple& 912 operator=(_Tuple&& __t) _NOEXCEPT_((is_nothrow_assignable<_BaseT&, _Tuple>::value)) 913 { 914 __base_.operator=(_VSTD::forward<_Tuple>(__t)); 915 return *this; 916 } 917 918 _LIBCPP_INLINE_VISIBILITY 919 void swap(tuple& __t) _NOEXCEPT_(__all<__is_nothrow_swappable<_Tp>::value...>::value) 920 {__base_.swap(__t.__base_);} 921}; 922 923template <> 924class _LIBCPP_TEMPLATE_VIS tuple<> 925{ 926public: 927 _LIBCPP_INLINE_VISIBILITY 928 _LIBCPP_CONSTEXPR tuple() _NOEXCEPT = default; 929 template <class _Alloc> 930 _LIBCPP_INLINE_VISIBILITY 931 tuple(allocator_arg_t, const _Alloc&) _NOEXCEPT {} 932 template <class _Alloc> 933 _LIBCPP_INLINE_VISIBILITY 934 tuple(allocator_arg_t, const _Alloc&, const tuple&) _NOEXCEPT {} 935 template <class _Up> 936 _LIBCPP_INLINE_VISIBILITY 937 tuple(array<_Up, 0>) _NOEXCEPT {} 938 template <class _Alloc, class _Up> 939 _LIBCPP_INLINE_VISIBILITY 940 tuple(allocator_arg_t, const _Alloc&, array<_Up, 0>) _NOEXCEPT {} 941 _LIBCPP_INLINE_VISIBILITY 942 void swap(tuple&) _NOEXCEPT {} 943}; 944 945#ifndef _LIBCPP_HAS_NO_DEDUCTION_GUIDES 946// NOTE: These are not yet standardized, but are required to simulate the 947// implicit deduction guide that should be generated had libc++ declared the 948// tuple-like constructors "correctly" 949template <class _Alloc, class ..._Args> 950tuple(allocator_arg_t, const _Alloc&, tuple<_Args...> const&) -> tuple<_Args...>; 951template <class _Alloc, class ..._Args> 952tuple(allocator_arg_t, const _Alloc&, tuple<_Args...>&&) -> tuple<_Args...>; 953#endif 954 955template <class ..._Tp> 956inline _LIBCPP_INLINE_VISIBILITY 957typename enable_if 958< 959 __all<__is_swappable<_Tp>::value...>::value, 960 void 961>::type 962swap(tuple<_Tp...>& __t, tuple<_Tp...>& __u) 963 _NOEXCEPT_(__all<__is_nothrow_swappable<_Tp>::value...>::value) 964 {__t.swap(__u);} 965 966// get 967 968template <size_t _Ip, class ..._Tp> 969inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 970typename tuple_element<_Ip, tuple<_Tp...> >::type& 971get(tuple<_Tp...>& __t) _NOEXCEPT 972{ 973 typedef _LIBCPP_NODEBUG_TYPE typename tuple_element<_Ip, tuple<_Tp...> >::type type; 974 return static_cast<__tuple_leaf<_Ip, type>&>(__t.__base_).get(); 975} 976 977template <size_t _Ip, class ..._Tp> 978inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 979const typename tuple_element<_Ip, tuple<_Tp...> >::type& 980get(const tuple<_Tp...>& __t) _NOEXCEPT 981{ 982 typedef _LIBCPP_NODEBUG_TYPE typename tuple_element<_Ip, tuple<_Tp...> >::type type; 983 return static_cast<const __tuple_leaf<_Ip, type>&>(__t.__base_).get(); 984} 985 986template <size_t _Ip, class ..._Tp> 987inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 988typename tuple_element<_Ip, tuple<_Tp...> >::type&& 989get(tuple<_Tp...>&& __t) _NOEXCEPT 990{ 991 typedef _LIBCPP_NODEBUG_TYPE typename tuple_element<_Ip, tuple<_Tp...> >::type type; 992 return static_cast<type&&>( 993 static_cast<__tuple_leaf<_Ip, type>&&>(__t.__base_).get()); 994} 995 996template <size_t _Ip, class ..._Tp> 997inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 998const typename tuple_element<_Ip, tuple<_Tp...> >::type&& 999get(const tuple<_Tp...>&& __t) _NOEXCEPT 1000{ 1001 typedef _LIBCPP_NODEBUG_TYPE typename tuple_element<_Ip, tuple<_Tp...> >::type type; 1002 return static_cast<const type&&>( 1003 static_cast<const __tuple_leaf<_Ip, type>&&>(__t.__base_).get()); 1004} 1005 1006#if _LIBCPP_STD_VER > 11 1007 1008namespace __find_detail { 1009 1010static constexpr size_t __not_found = -1; 1011static constexpr size_t __ambiguous = __not_found - 1; 1012 1013inline _LIBCPP_INLINE_VISIBILITY 1014constexpr size_t __find_idx_return(size_t __curr_i, size_t __res, bool __matches) { 1015 return !__matches ? __res : 1016 (__res == __not_found ? __curr_i : __ambiguous); 1017} 1018 1019template <size_t _Nx> 1020inline _LIBCPP_INLINE_VISIBILITY 1021constexpr size_t __find_idx(size_t __i, const bool (&__matches)[_Nx]) { 1022 return __i == _Nx ? __not_found : 1023 __find_idx_return(__i, __find_idx(__i + 1, __matches), __matches[__i]); 1024} 1025 1026template <class _T1, class ..._Args> 1027struct __find_exactly_one_checked { 1028 static constexpr bool __matches[sizeof...(_Args)] = {is_same<_T1, _Args>::value...}; 1029 static constexpr size_t value = __find_detail::__find_idx(0, __matches); 1030 static_assert(value != __not_found, "type not found in type list" ); 1031 static_assert(value != __ambiguous, "type occurs more than once in type list"); 1032}; 1033 1034template <class _T1> 1035struct __find_exactly_one_checked<_T1> { 1036 static_assert(!is_same<_T1, _T1>::value, "type not in empty type list"); 1037}; 1038 1039} // namespace __find_detail; 1040 1041template <typename _T1, typename... _Args> 1042struct __find_exactly_one_t 1043 : public __find_detail::__find_exactly_one_checked<_T1, _Args...> { 1044}; 1045 1046template <class _T1, class... _Args> 1047inline _LIBCPP_INLINE_VISIBILITY 1048constexpr _T1& get(tuple<_Args...>& __tup) noexcept 1049{ 1050 return _VSTD::get<__find_exactly_one_t<_T1, _Args...>::value>(__tup); 1051} 1052 1053template <class _T1, class... _Args> 1054inline _LIBCPP_INLINE_VISIBILITY 1055constexpr _T1 const& get(tuple<_Args...> const& __tup) noexcept 1056{ 1057 return _VSTD::get<__find_exactly_one_t<_T1, _Args...>::value>(__tup); 1058} 1059 1060template <class _T1, class... _Args> 1061inline _LIBCPP_INLINE_VISIBILITY 1062constexpr _T1&& get(tuple<_Args...>&& __tup) noexcept 1063{ 1064 return _VSTD::get<__find_exactly_one_t<_T1, _Args...>::value>(_VSTD::move(__tup)); 1065} 1066 1067template <class _T1, class... _Args> 1068inline _LIBCPP_INLINE_VISIBILITY 1069constexpr _T1 const&& get(tuple<_Args...> const&& __tup) noexcept 1070{ 1071 return _VSTD::get<__find_exactly_one_t<_T1, _Args...>::value>(_VSTD::move(__tup)); 1072} 1073 1074#endif 1075 1076// tie 1077 1078template <class ..._Tp> 1079inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1080tuple<_Tp&...> 1081tie(_Tp&... __t) _NOEXCEPT 1082{ 1083 return tuple<_Tp&...>(__t...); 1084} 1085 1086template <class _Up> 1087struct __ignore_t 1088{ 1089 template <class _Tp> 1090 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1091 const __ignore_t& operator=(_Tp&&) const {return *this;} 1092}; 1093 1094namespace { 1095 _LIBCPP_INLINE_VAR constexpr __ignore_t<unsigned char> ignore = __ignore_t<unsigned char>(); 1096} 1097 1098template <class... _Tp> 1099inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1100tuple<typename __unwrap_ref_decay<_Tp>::type...> 1101make_tuple(_Tp&&... __t) 1102{ 1103 return tuple<typename __unwrap_ref_decay<_Tp>::type...>(_VSTD::forward<_Tp>(__t)...); 1104} 1105 1106template <class... _Tp> 1107inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1108tuple<_Tp&&...> 1109forward_as_tuple(_Tp&&... __t) _NOEXCEPT 1110{ 1111 return tuple<_Tp&&...>(_VSTD::forward<_Tp>(__t)...); 1112} 1113 1114template <size_t _Ip> 1115struct __tuple_equal 1116{ 1117 template <class _Tp, class _Up> 1118 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1119 bool operator()(const _Tp& __x, const _Up& __y) 1120 { 1121 return __tuple_equal<_Ip - 1>()(__x, __y) && _VSTD::get<_Ip-1>(__x) == _VSTD::get<_Ip-1>(__y); 1122 } 1123}; 1124 1125template <> 1126struct __tuple_equal<0> 1127{ 1128 template <class _Tp, class _Up> 1129 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1130 bool operator()(const _Tp&, const _Up&) 1131 { 1132 return true; 1133 } 1134}; 1135 1136template <class ..._Tp, class ..._Up> 1137inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1138bool 1139operator==(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) 1140{ 1141 static_assert (sizeof...(_Tp) == sizeof...(_Up), "Can't compare tuples of different sizes"); 1142 return __tuple_equal<sizeof...(_Tp)>()(__x, __y); 1143} 1144 1145template <class ..._Tp, class ..._Up> 1146inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1147bool 1148operator!=(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) 1149{ 1150 return !(__x == __y); 1151} 1152 1153template <size_t _Ip> 1154struct __tuple_less 1155{ 1156 template <class _Tp, class _Up> 1157 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1158 bool operator()(const _Tp& __x, const _Up& __y) 1159 { 1160 const size_t __idx = tuple_size<_Tp>::value - _Ip; 1161 if (_VSTD::get<__idx>(__x) < _VSTD::get<__idx>(__y)) 1162 return true; 1163 if (_VSTD::get<__idx>(__y) < _VSTD::get<__idx>(__x)) 1164 return false; 1165 return __tuple_less<_Ip-1>()(__x, __y); 1166 } 1167}; 1168 1169template <> 1170struct __tuple_less<0> 1171{ 1172 template <class _Tp, class _Up> 1173 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1174 bool operator()(const _Tp&, const _Up&) 1175 { 1176 return false; 1177 } 1178}; 1179 1180template <class ..._Tp, class ..._Up> 1181inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1182bool 1183operator<(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) 1184{ 1185 static_assert (sizeof...(_Tp) == sizeof...(_Up), "Can't compare tuples of different sizes"); 1186 return __tuple_less<sizeof...(_Tp)>()(__x, __y); 1187} 1188 1189template <class ..._Tp, class ..._Up> 1190inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1191bool 1192operator>(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) 1193{ 1194 return __y < __x; 1195} 1196 1197template <class ..._Tp, class ..._Up> 1198inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1199bool 1200operator>=(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) 1201{ 1202 return !(__x < __y); 1203} 1204 1205template <class ..._Tp, class ..._Up> 1206inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1207bool 1208operator<=(const tuple<_Tp...>& __x, const tuple<_Up...>& __y) 1209{ 1210 return !(__y < __x); 1211} 1212 1213// tuple_cat 1214 1215template <class _Tp, class _Up> struct __tuple_cat_type; 1216 1217template <class ..._Ttypes, class ..._Utypes> 1218struct __tuple_cat_type<tuple<_Ttypes...>, __tuple_types<_Utypes...> > 1219{ 1220 typedef _LIBCPP_NODEBUG_TYPE tuple<_Ttypes..., _Utypes...> type; 1221}; 1222 1223template <class _ResultTuple, bool _Is_Tuple0TupleLike, class ..._Tuples> 1224struct __tuple_cat_return_1 1225{ 1226}; 1227 1228template <class ..._Types, class _Tuple0> 1229struct __tuple_cat_return_1<tuple<_Types...>, true, _Tuple0> 1230{ 1231 typedef _LIBCPP_NODEBUG_TYPE typename __tuple_cat_type<tuple<_Types...>, 1232 typename __make_tuple_types<typename __uncvref<_Tuple0>::type>::type>::type 1233 type; 1234}; 1235 1236template <class ..._Types, class _Tuple0, class _Tuple1, class ..._Tuples> 1237struct __tuple_cat_return_1<tuple<_Types...>, true, _Tuple0, _Tuple1, _Tuples...> 1238 : public __tuple_cat_return_1< 1239 typename __tuple_cat_type< 1240 tuple<_Types...>, 1241 typename __make_tuple_types<typename __uncvref<_Tuple0>::type>::type 1242 >::type, 1243 __tuple_like<typename remove_reference<_Tuple1>::type>::value, 1244 _Tuple1, _Tuples...> 1245{ 1246}; 1247 1248template <class ..._Tuples> struct __tuple_cat_return; 1249 1250template <class _Tuple0, class ..._Tuples> 1251struct __tuple_cat_return<_Tuple0, _Tuples...> 1252 : public __tuple_cat_return_1<tuple<>, 1253 __tuple_like<typename remove_reference<_Tuple0>::type>::value, _Tuple0, 1254 _Tuples...> 1255{ 1256}; 1257 1258template <> 1259struct __tuple_cat_return<> 1260{ 1261 typedef _LIBCPP_NODEBUG_TYPE tuple<> type; 1262}; 1263 1264inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1265tuple<> 1266tuple_cat() 1267{ 1268 return tuple<>(); 1269} 1270 1271template <class _Rp, class _Indices, class _Tuple0, class ..._Tuples> 1272struct __tuple_cat_return_ref_imp; 1273 1274template <class ..._Types, size_t ..._I0, class _Tuple0> 1275struct __tuple_cat_return_ref_imp<tuple<_Types...>, __tuple_indices<_I0...>, _Tuple0> 1276{ 1277 typedef _LIBCPP_NODEBUG_TYPE typename remove_reference<_Tuple0>::type _T0; 1278 typedef tuple<_Types..., typename __apply_cv<_Tuple0, 1279 typename tuple_element<_I0, _T0>::type>::type&&...> type; 1280}; 1281 1282template <class ..._Types, size_t ..._I0, class _Tuple0, class _Tuple1, class ..._Tuples> 1283struct __tuple_cat_return_ref_imp<tuple<_Types...>, __tuple_indices<_I0...>, 1284 _Tuple0, _Tuple1, _Tuples...> 1285 : public __tuple_cat_return_ref_imp< 1286 tuple<_Types..., typename __apply_cv<_Tuple0, 1287 typename tuple_element<_I0, 1288 typename remove_reference<_Tuple0>::type>::type>::type&&...>, 1289 typename __make_tuple_indices<tuple_size<typename 1290 remove_reference<_Tuple1>::type>::value>::type, 1291 _Tuple1, _Tuples...> 1292{ 1293}; 1294 1295template <class _Tuple0, class ..._Tuples> 1296struct __tuple_cat_return_ref 1297 : public __tuple_cat_return_ref_imp<tuple<>, 1298 typename __make_tuple_indices< 1299 tuple_size<typename remove_reference<_Tuple0>::type>::value 1300 >::type, _Tuple0, _Tuples...> 1301{ 1302}; 1303 1304template <class _Types, class _I0, class _J0> 1305struct __tuple_cat; 1306 1307template <class ..._Types, size_t ..._I0, size_t ..._J0> 1308struct __tuple_cat<tuple<_Types...>, __tuple_indices<_I0...>, __tuple_indices<_J0...> > 1309{ 1310 template <class _Tuple0> 1311 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1312 typename __tuple_cat_return_ref<tuple<_Types...>&&, _Tuple0&&>::type 1313 operator()(tuple<_Types...> __t, _Tuple0&& __t0) 1314 { 1315 return forward_as_tuple(_VSTD::forward<_Types>(_VSTD::get<_I0>(__t))..., 1316 _VSTD::get<_J0>(_VSTD::forward<_Tuple0>(__t0))...); 1317 } 1318 1319 template <class _Tuple0, class _Tuple1, class ..._Tuples> 1320 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1321 typename __tuple_cat_return_ref<tuple<_Types...>&&, _Tuple0&&, _Tuple1&&, _Tuples&&...>::type 1322 operator()(tuple<_Types...> __t, _Tuple0&& __t0, _Tuple1&& __t1, _Tuples&& ...__tpls) 1323 { 1324 typedef _LIBCPP_NODEBUG_TYPE typename remove_reference<_Tuple0>::type _T0; 1325 typedef _LIBCPP_NODEBUG_TYPE typename remove_reference<_Tuple1>::type _T1; 1326 return __tuple_cat< 1327 tuple<_Types..., typename __apply_cv<_Tuple0, typename tuple_element<_J0, _T0>::type>::type&&...>, 1328 typename __make_tuple_indices<sizeof ...(_Types) + tuple_size<_T0>::value>::type, 1329 typename __make_tuple_indices<tuple_size<_T1>::value>::type>() 1330 (forward_as_tuple( 1331 _VSTD::forward<_Types>(_VSTD::get<_I0>(__t))..., 1332 _VSTD::get<_J0>(_VSTD::forward<_Tuple0>(__t0))... 1333 ), 1334 _VSTD::forward<_Tuple1>(__t1), 1335 _VSTD::forward<_Tuples>(__tpls)...); 1336 } 1337}; 1338 1339template <class _Tuple0, class... _Tuples> 1340inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR_AFTER_CXX11 1341typename __tuple_cat_return<_Tuple0, _Tuples...>::type 1342tuple_cat(_Tuple0&& __t0, _Tuples&&... __tpls) 1343{ 1344 typedef _LIBCPP_NODEBUG_TYPE typename remove_reference<_Tuple0>::type _T0; 1345 return __tuple_cat<tuple<>, __tuple_indices<>, 1346 typename __make_tuple_indices<tuple_size<_T0>::value>::type>() 1347 (tuple<>(), _VSTD::forward<_Tuple0>(__t0), 1348 _VSTD::forward<_Tuples>(__tpls)...); 1349} 1350 1351template <class ..._Tp, class _Alloc> 1352struct _LIBCPP_TEMPLATE_VIS uses_allocator<tuple<_Tp...>, _Alloc> 1353 : true_type {}; 1354 1355template <class _T1, class _T2> 1356template <class... _Args1, class... _Args2, size_t ..._I1, size_t ..._I2> 1357inline _LIBCPP_INLINE_VISIBILITY 1358pair<_T1, _T2>::pair(piecewise_construct_t, 1359 tuple<_Args1...>& __first_args, tuple<_Args2...>& __second_args, 1360 __tuple_indices<_I1...>, __tuple_indices<_I2...>) 1361 : first(_VSTD::forward<_Args1>(_VSTD::get<_I1>( __first_args))...), 1362 second(_VSTD::forward<_Args2>(_VSTD::get<_I2>(__second_args))...) 1363{ 1364} 1365 1366#if _LIBCPP_STD_VER > 14 1367template <class _Tp> 1368_LIBCPP_INLINE_VAR constexpr size_t tuple_size_v = tuple_size<_Tp>::value; 1369 1370#define _LIBCPP_NOEXCEPT_RETURN(...) noexcept(noexcept(__VA_ARGS__)) { return __VA_ARGS__; } 1371 1372template <class _Fn, class _Tuple, size_t ..._Id> 1373inline _LIBCPP_INLINE_VISIBILITY 1374constexpr decltype(auto) __apply_tuple_impl(_Fn && __f, _Tuple && __t, 1375 __tuple_indices<_Id...>) 1376_LIBCPP_NOEXCEPT_RETURN( 1377 _VSTD::__invoke_constexpr( 1378 _VSTD::forward<_Fn>(__f), 1379 _VSTD::get<_Id>(_VSTD::forward<_Tuple>(__t))...) 1380) 1381 1382template <class _Fn, class _Tuple> 1383inline _LIBCPP_INLINE_VISIBILITY 1384constexpr decltype(auto) apply(_Fn && __f, _Tuple && __t) 1385_LIBCPP_NOEXCEPT_RETURN( 1386 _VSTD::__apply_tuple_impl( 1387 _VSTD::forward<_Fn>(__f), _VSTD::forward<_Tuple>(__t), 1388 typename __make_tuple_indices<tuple_size_v<remove_reference_t<_Tuple>>>::type{}) 1389) 1390 1391template <class _Tp, class _Tuple, size_t... _Idx> 1392inline _LIBCPP_INLINE_VISIBILITY 1393constexpr _Tp __make_from_tuple_impl(_Tuple&& __t, __tuple_indices<_Idx...>) 1394_LIBCPP_NOEXCEPT_RETURN( 1395 _Tp(_VSTD::get<_Idx>(_VSTD::forward<_Tuple>(__t))...) 1396) 1397 1398template <class _Tp, class _Tuple> 1399inline _LIBCPP_INLINE_VISIBILITY 1400constexpr _Tp make_from_tuple(_Tuple&& __t) 1401_LIBCPP_NOEXCEPT_RETURN( 1402 _VSTD::__make_from_tuple_impl<_Tp>(_VSTD::forward<_Tuple>(__t), 1403 typename __make_tuple_indices<tuple_size_v<remove_reference_t<_Tuple>>>::type{}) 1404) 1405 1406#undef _LIBCPP_NOEXCEPT_RETURN 1407 1408#endif // _LIBCPP_STD_VER > 14 1409 1410#endif // !defined(_LIBCPP_CXX03_LANG) 1411 1412_LIBCPP_END_NAMESPACE_STD 1413 1414#endif // _LIBCPP_TUPLE 1415