| author | |
| committer | |
| log | 0d4e223ab58974361ea4dfbad82f2109cd5da664 |
| tree | 79ff129af24ecb581ed692134f56716af0f0f6a1 |
| parent | cef9aaa456e776b77ac6283d97556c490db2ff16 |
22 files changed, 644 insertions(+), 652 deletions(-)
lib/libcxx/include/__algorithm/ranges_binary_search.h+2-2| ... | ... | @@ -36,7 +36,7 @@ struct __fn { |
| 36 | 36 | _LIBCPP_NODISCARD_EXT _LIBCPP_HIDE_FROM_ABI constexpr |
| 37 | 37 | bool operator()(_Iter __first, _Sent __last, const _Type& __value, _Comp __comp = {}, _Proj __proj = {}) const { |
| 38 | 38 | auto __ret = std::__lower_bound_impl<_RangeAlgPolicy>(__first, __last, __value, __comp, __proj); |
| 39 | return __ret != __last && !std::invoke(__comp, __value, std::invoke(__proj, *__first)); | |
| 39 | return __ret != __last && !std::invoke(__comp, __value, std::invoke(__proj, *__ret)); | |
| 40 | 40 | } |
| 41 | 41 | |
| 42 | 42 | template <forward_range _Range, class _Type, class _Proj = identity, |
| ... | ... | @@ -46,7 +46,7 @@ struct __fn { |
| 46 | 46 | auto __first = ranges::begin(__r); |
| 47 | 47 | auto __last = ranges::end(__r); |
| 48 | 48 | auto __ret = std::__lower_bound_impl<_RangeAlgPolicy>(__first, __last, __value, __comp, __proj); |
| 49 | return __ret != __last && !std::invoke(__comp, __value, std::invoke(__proj, *__first)); | |
| 49 | return __ret != __last && !std::invoke(__comp, __value, std::invoke(__proj, *__ret)); | |
| 50 | 50 | } |
| 51 | 51 | }; |
| 52 | 52 | } // namespace __binary_search |
lib/libcxx/include/__config+22-7| ... | ... | @@ -134,6 +134,15 @@ |
| 134 | 134 | # define _LIBCPP_ABI_DO_NOT_EXPORT_VECTOR_BASE_COMMON |
| 135 | 135 | // According to the Standard, `bitset::operator[] const` returns bool |
| 136 | 136 | # define _LIBCPP_ABI_BITSET_VECTOR_BOOL_CONST_SUBSCRIPT_RETURN_BOOL |
| 137 | // Fix the implementation of CityHash used for std::hash<fundamental-type>. | |
| 138 | // This is an ABI break because `std::hash` will return a different result, | |
| 139 | // which means that hashing the same object in translation units built against | |
| 140 | // different versions of libc++ can return inconsistent results. This is especially | |
| 141 | // tricky since std::hash is used in the implementation of unordered containers. | |
| 142 | // | |
| 143 | // The incorrect implementation of CityHash has the problem that it drops some | |
| 144 | // bits on the floor. | |
| 145 | # define _LIBCPP_ABI_FIX_CITYHASH_IMPLEMENTATION | |
| 137 | 146 | // Remove the base 10 implementation of std::to_chars from the dylib. |
| 138 | 147 | // The implementation moved to the header, but we still export the symbols from |
| 139 | 148 | // the dylib for backwards compatibility. |
| ... | ... | @@ -895,7 +904,7 @@ _LIBCPP_BEGIN_NAMESPACE_STD _LIBCPP_END_NAMESPACE_STD |
| 895 | 904 | |
| 896 | 905 | // Try to find out if RTTI is disabled. |
| 897 | 906 | # if !defined(__cpp_rtti) || __cpp_rtti < 199711L |
| 898 | # define _LIBCPP_NO_RTTI | |
| 907 | # define _LIBCPP_HAS_NO_RTTI | |
| 899 | 908 | # endif |
| 900 | 909 | |
| 901 | 910 | # ifndef _LIBCPP_WEAK |
| ... | ... | @@ -1227,12 +1236,12 @@ _LIBCPP_BEGIN_NAMESPACE_STD _LIBCPP_END_NAMESPACE_STD |
| 1227 | 1236 | // functions are declared by the C library. |
| 1228 | 1237 | # define _LIBCPP_HAS_NO_C8RTOMB_MBRTOC8 |
| 1229 | 1238 | // GNU libc 2.36 and newer declare c8rtomb() and mbrtoc8() in C++ modes if |
| 1230 | // __cpp_char8_t is defined or if C2X extensions are enabled. Unfortunately, | |
| 1231 | // determining the latter depends on internal GNU libc details. If the | |
| 1232 | // __cpp_char8_t feature test macro is not defined, then a char8_t typedef | |
| 1233 | // will be declared as well. | |
| 1234 | # if defined(_LIBCPP_GLIBC_PREREQ) && defined(__GLIBC_USE) | |
| 1235 | # if _LIBCPP_GLIBC_PREREQ(2, 36) && (defined(__cpp_char8_t) || __GLIBC_USE(ISOC2X)) | |
| 1239 | // __cpp_char8_t is defined or if C2X extensions are enabled. Determining | |
| 1240 | // the latter depends on internal GNU libc details that are not appropriate | |
| 1241 | // to depend on here, so any declarations present when __cpp_char8_t is not | |
| 1242 | // defined are ignored. | |
| 1243 | # if defined(_LIBCPP_GLIBC_PREREQ) | |
| 1244 | # if _LIBCPP_GLIBC_PREREQ(2, 36) && defined(__cpp_char8_t) | |
| 1236 | 1245 | # undef _LIBCPP_HAS_NO_C8RTOMB_MBRTOC8 |
| 1237 | 1246 | # endif |
| 1238 | 1247 | # endif |
| ... | ... | @@ -1250,6 +1259,12 @@ _LIBCPP_BEGIN_NAMESPACE_STD _LIBCPP_END_NAMESPACE_STD |
| 1250 | 1259 | # define _LIBCPP_CTAD_SUPPORTED_FOR_TYPE(_ClassName) static_assert(true, "") |
| 1251 | 1260 | #endif |
| 1252 | 1261 | |
| 1262 | // TODO(varconst): currently, there are bugs in Clang's intrinsics when handling Objective-C++ `id`, so don't use | |
| 1263 | // compiler intrinsics in the Objective-C++ mode. | |
| 1264 | # ifdef __OBJC__ | |
| 1265 | # define _LIBCPP_WORKAROUND_OBJCXX_COMPILER_INTRINSICS | |
| 1266 | # endif | |
| 1267 | ||
| 1253 | 1268 | #endif // __cplusplus |
| 1254 | 1269 | |
| 1255 | 1270 | #endif // _LIBCPP___CONFIG |
lib/libcxx/include/__format/concepts.h+2-3| ... | ... | @@ -66,9 +66,8 @@ concept formattable = __formattable<_Tp, _CharT>; |
| 66 | 66 | // TODO FMT Add a test to validate we fail when using that concept after P2165 |
| 67 | 67 | // has been implemented. |
| 68 | 68 | template <class _Tp> |
| 69 | concept __fmt_pair_like = __is_specialization_v<_Tp, pair> || | |
| 70 | // Use a requires since tuple_size_v may fail to instantiate, | |
| 71 | (__is_specialization_v<_Tp, tuple> && requires { tuple_size_v<_Tp> == 2; }); | |
| 69 | concept __fmt_pair_like = | |
| 70 | __is_specialization_v<_Tp, pair> || (__is_specialization_v<_Tp, tuple> && tuple_size_v<_Tp> == 2); | |
| 72 | 71 | |
| 73 | 72 | # endif //_LIBCPP_STD_VER > 20 |
| 74 | 73 | #endif //_LIBCPP_STD_VER > 17 |
lib/libcxx/include/__format/format_functions.h+5-3| ... | ... | @@ -258,10 +258,12 @@ __handle_replacement_field(const _CharT* __begin, const _CharT* __end, |
| 258 | 258 | |
| 259 | 259 | if constexpr (same_as<_Ctx, __compile_time_basic_format_context<_CharT>>) { |
| 260 | 260 | __arg_t __type = __ctx.arg(__r.__value); |
| 261 | if (__type == __arg_t::__handle) | |
| 261 | if (__type == __arg_t::__none) | |
| 262 | std::__throw_format_error("Argument index out of bounds"); | |
| 263 | else if (__type == __arg_t::__handle) | |
| 262 | 264 | __ctx.__handle(__r.__value).__parse(__parse_ctx); |
| 263 | else | |
| 264 | __format::__compile_time_visit_format_arg(__parse_ctx, __ctx, __type); | |
| 265 | else if (__parse) | |
| 266 | __format::__compile_time_visit_format_arg(__parse_ctx, __ctx, __type); | |
| 265 | 267 | } else |
| 266 | 268 | _VSTD::__visit_format_arg( |
| 267 | 269 | [&](auto __arg) { |
lib/libcxx/include/__format/formatter_floating_point.h+1-2| ... | ... | @@ -404,7 +404,6 @@ _LIBCPP_HIDE_FROM_ABI __float_result __format_buffer_general_lower_case(__float_ |
| 404 | 404 | // In fixed mode the algorithm truncates trailing spaces and possibly the |
| 405 | 405 | // radix point. There's no good guess for the position of the radix point |
| 406 | 406 | // therefore scan the output after the first digit. |
| 407 | ||
| 408 | 407 | __result.__radix_point = _VSTD::find(__first, __result.__last, '.'); |
| 409 | 408 | } |
| 410 | 409 | } |
| ... | ... | @@ -665,7 +664,7 @@ __format_floating_point(_Tp __value, auto& __ctx, __format_spec::__parsed_specif |
| 665 | 664 | if (__result.__exponent == __result.__last) |
| 666 | 665 | // if P > X >= -4, the conversion is with style f or F and precision P - 1 - X. |
| 667 | 666 | // By including the radix point it calculates P - (1 + X) |
| 668 | __p -= __result.__radix_point - __buffer.begin(); | |
| 667 | __p -= __result.__radix_point - __result.__integral; | |
| 669 | 668 | else |
| 670 | 669 | // otherwise, the conversion is with style e or E and precision P - 1. |
| 671 | 670 | --__p; |
lib/libcxx/include/__functional/function.h+19-19| ... | ... | @@ -268,10 +268,10 @@ public: |
| 268 | 268 | virtual void destroy() _NOEXCEPT = 0; |
| 269 | 269 | virtual void destroy_deallocate() _NOEXCEPT = 0; |
| 270 | 270 | virtual _Rp operator()(_ArgTypes&& ...) = 0; |
| 271 | #ifndef _LIBCPP_NO_RTTI | |
| 271 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 272 | 272 | virtual const void* target(const type_info&) const _NOEXCEPT = 0; |
| 273 | 273 | virtual const std::type_info& target_type() const _NOEXCEPT = 0; |
| 274 | #endif // _LIBCPP_NO_RTTI | |
| 274 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 275 | 275 | }; |
| 276 | 276 | |
| 277 | 277 | // __func implements __base for a given functor type. |
| ... | ... | @@ -305,10 +305,10 @@ public: |
| 305 | 305 | virtual void destroy() _NOEXCEPT; |
| 306 | 306 | virtual void destroy_deallocate() _NOEXCEPT; |
| 307 | 307 | virtual _Rp operator()(_ArgTypes&&... __arg); |
| 308 | #ifndef _LIBCPP_NO_RTTI | |
| 308 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 309 | 309 | virtual const void* target(const type_info&) const _NOEXCEPT; |
| 310 | 310 | virtual const std::type_info& target_type() const _NOEXCEPT; |
| 311 | #endif // _LIBCPP_NO_RTTI | |
| 311 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 312 | 312 | }; |
| 313 | 313 | |
| 314 | 314 | template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes> |
| ... | ... | @@ -356,7 +356,7 @@ __func<_Fp, _Alloc, _Rp(_ArgTypes...)>::operator()(_ArgTypes&& ... __arg) |
| 356 | 356 | return __f_(_VSTD::forward<_ArgTypes>(__arg)...); |
| 357 | 357 | } |
| 358 | 358 | |
| 359 | #ifndef _LIBCPP_NO_RTTI | |
| 359 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 360 | 360 | |
| 361 | 361 | template<class _Fp, class _Alloc, class _Rp, class ..._ArgTypes> |
| 362 | 362 | const void* |
| ... | ... | @@ -374,7 +374,7 @@ __func<_Fp, _Alloc, _Rp(_ArgTypes...)>::target_type() const _NOEXCEPT |
| 374 | 374 | return typeid(_Fp); |
| 375 | 375 | } |
| 376 | 376 | |
| 377 | #endif // _LIBCPP_NO_RTTI | |
| 377 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 378 | 378 | |
| 379 | 379 | // __value_func creates a value-type from a __func. |
| 380 | 380 | |
| ... | ... | @@ -553,7 +553,7 @@ template <class _Rp, class... _ArgTypes> class __value_func<_Rp(_ArgTypes...)> |
| 553 | 553 | _LIBCPP_INLINE_VISIBILITY |
| 554 | 554 | explicit operator bool() const _NOEXCEPT { return __f_ != nullptr; } |
| 555 | 555 | |
| 556 | #ifndef _LIBCPP_NO_RTTI | |
| 556 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 557 | 557 | _LIBCPP_INLINE_VISIBILITY |
| 558 | 558 | const std::type_info& target_type() const _NOEXCEPT |
| 559 | 559 | { |
| ... | ... | @@ -569,7 +569,7 @@ template <class _Rp, class... _ArgTypes> class __value_func<_Rp(_ArgTypes...)> |
| 569 | 569 | return nullptr; |
| 570 | 570 | return (const _Tp*)__f_->target(typeid(_Tp)); |
| 571 | 571 | } |
| 572 | #endif // _LIBCPP_NO_RTTI | |
| 572 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 573 | 573 | }; |
| 574 | 574 | |
| 575 | 575 | // Storage for a functor object, to be used with __policy to manage copy and |
| ... | ... | @@ -616,7 +616,7 @@ struct __policy |
| 616 | 616 | { |
| 617 | 617 | static const _LIBCPP_CONSTEXPR __policy __policy_ = {nullptr, nullptr, |
| 618 | 618 | true, |
| 619 | #ifndef _LIBCPP_NO_RTTI | |
| 619 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 620 | 620 | &typeid(void) |
| 621 | 621 | #else |
| 622 | 622 | nullptr |
| ... | ... | @@ -642,7 +642,7 @@ struct __policy |
| 642 | 642 | __choose_policy(/* is_small = */ false_type) { |
| 643 | 643 | static const _LIBCPP_CONSTEXPR __policy __policy_ = { |
| 644 | 644 | &__large_clone<_Fun>, &__large_destroy<_Fun>, false, |
| 645 | #ifndef _LIBCPP_NO_RTTI | |
| 645 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 646 | 646 | &typeid(typename _Fun::_Target) |
| 647 | 647 | #else |
| 648 | 648 | nullptr |
| ... | ... | @@ -657,7 +657,7 @@ struct __policy |
| 657 | 657 | { |
| 658 | 658 | static const _LIBCPP_CONSTEXPR __policy __policy_ = { |
| 659 | 659 | nullptr, nullptr, false, |
| 660 | #ifndef _LIBCPP_NO_RTTI | |
| 660 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 661 | 661 | &typeid(typename _Fun::_Target) |
| 662 | 662 | #else |
| 663 | 663 | nullptr |
| ... | ... | @@ -861,7 +861,7 @@ template <class _Rp, class... _ArgTypes> class __policy_func<_Rp(_ArgTypes...)> |
| 861 | 861 | return !__policy_->__is_null; |
| 862 | 862 | } |
| 863 | 863 | |
| 864 | #ifndef _LIBCPP_NO_RTTI | |
| 864 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 865 | 865 | _LIBCPP_INLINE_VISIBILITY |
| 866 | 866 | const std::type_info& target_type() const _NOEXCEPT |
| 867 | 867 | { |
| ... | ... | @@ -878,7 +878,7 @@ template <class _Rp, class... _ArgTypes> class __policy_func<_Rp(_ArgTypes...)> |
| 878 | 878 | else |
| 879 | 879 | return reinterpret_cast<const _Tp*>(&__buf_.__small); |
| 880 | 880 | } |
| 881 | #endif // _LIBCPP_NO_RTTI | |
| 881 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 882 | 882 | }; |
| 883 | 883 | |
| 884 | 884 | #if defined(_LIBCPP_HAS_BLOCKS_RUNTIME) |
| ... | ... | @@ -945,7 +945,7 @@ public: |
| 945 | 945 | return _VSTD::__invoke(__f_, _VSTD::forward<_ArgTypes>(__arg)...); |
| 946 | 946 | } |
| 947 | 947 | |
| 948 | #ifndef _LIBCPP_NO_RTTI | |
| 948 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 949 | 949 | virtual const void* target(type_info const& __ti) const _NOEXCEPT { |
| 950 | 950 | if (__ti == typeid(__func::__block_type)) |
| 951 | 951 | return &__f_; |
| ... | ... | @@ -955,7 +955,7 @@ public: |
| 955 | 955 | virtual const std::type_info& target_type() const _NOEXCEPT { |
| 956 | 956 | return typeid(__func::__block_type); |
| 957 | 957 | } |
| 958 | #endif // _LIBCPP_NO_RTTI | |
| 958 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 959 | 959 | }; |
| 960 | 960 | |
| 961 | 961 | #endif // _LIBCPP_HAS_EXTENSION_BLOCKS |
| ... | ... | @@ -1056,12 +1056,12 @@ public: |
| 1056 | 1056 | // function invocation: |
| 1057 | 1057 | _Rp operator()(_ArgTypes...) const; |
| 1058 | 1058 | |
| 1059 | #ifndef _LIBCPP_NO_RTTI | |
| 1059 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 1060 | 1060 | // function target access: |
| 1061 | 1061 | const std::type_info& target_type() const _NOEXCEPT; |
| 1062 | 1062 | template <typename _Tp> _Tp* target() _NOEXCEPT; |
| 1063 | 1063 | template <typename _Tp> const _Tp* target() const _NOEXCEPT; |
| 1064 | #endif // _LIBCPP_NO_RTTI | |
| 1064 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 1065 | 1065 | }; |
| 1066 | 1066 | |
| 1067 | 1067 | #if _LIBCPP_STD_VER >= 17 |
| ... | ... | @@ -1156,7 +1156,7 @@ function<_Rp(_ArgTypes...)>::operator()(_ArgTypes... __arg) const |
| 1156 | 1156 | return __f_(_VSTD::forward<_ArgTypes>(__arg)...); |
| 1157 | 1157 | } |
| 1158 | 1158 | |
| 1159 | #ifndef _LIBCPP_NO_RTTI | |
| 1159 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 1160 | 1160 | |
| 1161 | 1161 | template<class _Rp, class ..._ArgTypes> |
| 1162 | 1162 | const std::type_info& |
| ... | ... | @@ -1181,7 +1181,7 @@ function<_Rp(_ArgTypes...)>::target() const _NOEXCEPT |
| 1181 | 1181 | return __f_.template target<_Tp>(); |
| 1182 | 1182 | } |
| 1183 | 1183 | |
| 1184 | #endif // _LIBCPP_NO_RTTI | |
| 1184 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 1185 | 1185 | |
| 1186 | 1186 | template <class _Rp, class... _ArgTypes> |
| 1187 | 1187 | inline _LIBCPP_INLINE_VISIBILITY |
lib/libcxx/include/__functional/hash.h+4| ... | ... | @@ -140,7 +140,11 @@ struct __murmur2_or_cityhash<_Size, 64> |
| 140 | 140 | if (__len >= 4) { |
| 141 | 141 | const uint32_t __a = std::__loadword<uint32_t>(__s); |
| 142 | 142 | const uint32_t __b = std::__loadword<uint32_t>(__s + __len - 4); |
| 143 | #ifdef _LIBCPP_ABI_FIX_CITYHASH_IMPLEMENTATION | |
| 143 | 144 | return __hash_len_16(__len + (static_cast<_Size>(__a) << 3), __b); |
| 145 | #else | |
| 146 | return __hash_len_16(__len + (__a << 3), __b); | |
| 147 | #endif | |
| 144 | 148 | } |
| 145 | 149 | if (__len > 0) { |
| 146 | 150 | const unsigned char __a = static_cast<unsigned char>(__s[0]); |
lib/libcxx/include/__memory/construct_at.h+10| ... | ... | @@ -83,6 +83,16 @@ _ForwardIterator __destroy(_ForwardIterator __first, _ForwardIterator __last) { |
| 83 | 83 | return __first; |
| 84 | 84 | } |
| 85 | 85 | |
| 86 | template <class _BidirectionalIterator> | |
| 87 | _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 | |
| 88 | _BidirectionalIterator __reverse_destroy(_BidirectionalIterator __first, _BidirectionalIterator __last) { | |
| 89 | while (__last != __first) { | |
| 90 | --__last; | |
| 91 | std::__destroy_at(std::addressof(*__last)); | |
| 92 | } | |
| 93 | return __last; | |
| 94 | } | |
| 95 | ||
| 86 | 96 | #if _LIBCPP_STD_VER > 14 |
| 87 | 97 | |
| 88 | 98 | template <class _Tp, enable_if_t<!is_array_v<_Tp>, int> = 0> |
lib/libcxx/include/__memory/shared_ptr.h+142-76| ... | ... | @@ -219,7 +219,7 @@ public: |
| 219 | 219 | __shared_ptr_pointer(_Tp __p, _Dp __d, _Alloc __a) |
| 220 | 220 | : __data_(__compressed_pair<_Tp, _Dp>(__p, _VSTD::move(__d)), _VSTD::move(__a)) {} |
| 221 | 221 | |
| 222 | #ifndef _LIBCPP_NO_RTTI | |
| 222 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 223 | 223 | const void* __get_deleter(const type_info&) const _NOEXCEPT override; |
| 224 | 224 | #endif |
| 225 | 225 | |
| ... | ... | @@ -228,7 +228,7 @@ private: |
| 228 | 228 | void __on_zero_shared_weak() _NOEXCEPT override; |
| 229 | 229 | }; |
| 230 | 230 | |
| 231 | #ifndef _LIBCPP_NO_RTTI | |
| 231 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 232 | 232 | |
| 233 | 233 | template <class _Tp, class _Dp, class _Alloc> |
| 234 | 234 | const void* |
| ... | ... | @@ -237,7 +237,7 @@ __shared_ptr_pointer<_Tp, _Dp, _Alloc>::__get_deleter(const type_info& __t) cons |
| 237 | 237 | return __t == typeid(_Dp) ? _VSTD::addressof(__data_.first().second()) : nullptr; |
| 238 | 238 | } |
| 239 | 239 | |
| 240 | #endif // _LIBCPP_NO_RTTI | |
| 240 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 241 | 241 | |
| 242 | 242 | template <class _Tp, class _Dp, class _Alloc> |
| 243 | 243 | void |
| ... | ... | @@ -260,7 +260,10 @@ __shared_ptr_pointer<_Tp, _Dp, _Alloc>::__on_zero_shared_weak() _NOEXCEPT |
| 260 | 260 | __a.deallocate(_PTraits::pointer_to(*this), 1); |
| 261 | 261 | } |
| 262 | 262 | |
| 263 | struct __default_initialize_tag {}; | |
| 263 | // This tag is used to instantiate an allocator type. The various shared_ptr control blocks | |
| 264 | // detect that the allocator has been instantiated for this type and perform alternative | |
| 265 | // initialization/destruction based on that. | |
| 266 | struct __for_overwrite_tag {}; | |
| 264 | 267 | |
| 265 | 268 | template <class _Tp, class _Alloc> |
| 266 | 269 | struct __shared_ptr_emplace |
| ... | ... | @@ -271,25 +274,20 @@ struct __shared_ptr_emplace |
| 271 | 274 | explicit __shared_ptr_emplace(_Alloc __a, _Args&& ...__args) |
| 272 | 275 | : __storage_(_VSTD::move(__a)) |
| 273 | 276 | { |
| 274 | #if _LIBCPP_STD_VER > 17 | |
| 275 | using _TpAlloc = typename __allocator_traits_rebind<_Alloc, _Tp>::type; | |
| 276 | _TpAlloc __tmp(*__get_alloc()); | |
| 277 | allocator_traits<_TpAlloc>::construct(__tmp, __get_elem(), _VSTD::forward<_Args>(__args)...); | |
| 277 | #if _LIBCPP_STD_VER >= 20 | |
| 278 | if constexpr (is_same_v<typename _Alloc::value_type, __for_overwrite_tag>) { | |
| 279 | static_assert(sizeof...(_Args) == 0, "No argument should be provided to the control block when using _for_overwrite"); | |
| 280 | ::new ((void*)__get_elem()) _Tp; | |
| 281 | } else { | |
| 282 | using _TpAlloc = typename __allocator_traits_rebind<_Alloc, _Tp>::type; | |
| 283 | _TpAlloc __tmp(*__get_alloc()); | |
| 284 | allocator_traits<_TpAlloc>::construct(__tmp, __get_elem(), _VSTD::forward<_Args>(__args)...); | |
| 285 | } | |
| 278 | 286 | #else |
| 279 | 287 | ::new ((void*)__get_elem()) _Tp(_VSTD::forward<_Args>(__args)...); |
| 280 | 288 | #endif |
| 281 | 289 | } |
| 282 | 290 | |
| 283 | ||
| 284 | #if _LIBCPP_STD_VER >= 20 | |
| 285 | _LIBCPP_HIDE_FROM_ABI | |
| 286 | explicit __shared_ptr_emplace(__default_initialize_tag, _Alloc __a) | |
| 287 | : __storage_(std::move(__a)) | |
| 288 | { | |
| 289 | ::new ((void*)__get_elem()) _Tp; | |
| 290 | } | |
| 291 | #endif | |
| 292 | ||
| 293 | 291 | _LIBCPP_HIDE_FROM_ABI |
| 294 | 292 | _Alloc* __get_alloc() _NOEXCEPT { return __storage_.__get_alloc(); } |
| 295 | 293 | |
| ... | ... | @@ -299,9 +297,13 @@ struct __shared_ptr_emplace |
| 299 | 297 | private: |
| 300 | 298 | void __on_zero_shared() _NOEXCEPT override { |
| 301 | 299 | #if _LIBCPP_STD_VER > 17 |
| 302 | using _TpAlloc = typename __allocator_traits_rebind<_Alloc, _Tp>::type; | |
| 303 | _TpAlloc __tmp(*__get_alloc()); | |
| 304 | allocator_traits<_TpAlloc>::destroy(__tmp, __get_elem()); | |
| 300 | if constexpr (is_same_v<typename _Alloc::value_type, __for_overwrite_tag>) { | |
| 301 | __get_elem()->~_Tp(); | |
| 302 | } else { | |
| 303 | using _TpAlloc = typename __allocator_traits_rebind<_Alloc, _Tp>::type; | |
| 304 | _TpAlloc __tmp(*__get_alloc()); | |
| 305 | allocator_traits<_TpAlloc>::destroy(__tmp, __get_elem()); | |
| 306 | } | |
| 305 | 307 | #else |
| 306 | 308 | __get_elem()->~_Tp(); |
| 307 | 309 | #endif |
| ... | ... | @@ -367,13 +369,57 @@ public: |
| 367 | 369 | |
| 368 | 370 | template<class _Tp> class _LIBCPP_TEMPLATE_VIS enable_shared_from_this; |
| 369 | 371 | |
| 370 | template<class _Tp, class _Up> | |
| 372 | // http://eel.is/c++draft/util.sharedptr#util.smartptr.shared.general-6 | |
| 373 | // A pointer type Y* is said to be compatible with a pointer type T* | |
| 374 | // when either Y* is convertible to T* or Y is U[N] and T is cv U[]. | |
| 375 | #if _LIBCPP_STD_VER >= 17 | |
| 376 | template <class _Yp, class _Tp> | |
| 377 | struct __bounded_convertible_to_unbounded : false_type {}; | |
| 378 | ||
| 379 | template <class _Up, std::size_t _Np, class _Tp> | |
| 380 | struct __bounded_convertible_to_unbounded<_Up[_Np], _Tp> | |
| 381 | : is_same<__remove_cv_t<_Tp>, _Up[]> {}; | |
| 382 | ||
| 383 | template <class _Yp, class _Tp> | |
| 371 | 384 | struct __compatible_with |
| 372 | #if _LIBCPP_STD_VER > 14 | |
| 373 | : is_convertible<remove_extent_t<_Tp>*, remove_extent_t<_Up>*> {}; | |
| 385 | : _Or< | |
| 386 | is_convertible<_Yp*, _Tp*>, | |
| 387 | __bounded_convertible_to_unbounded<_Yp, _Tp> | |
| 388 | > {}; | |
| 374 | 389 | #else |
| 375 | : is_convertible<_Tp*, _Up*> {}; | |
| 376 | #endif // _LIBCPP_STD_VER > 14 | |
| 390 | template <class _Yp, class _Tp> | |
| 391 | struct __compatible_with | |
| 392 | : is_convertible<_Yp*, _Tp*> {}; | |
| 393 | #endif // _LIBCPP_STD_VER >= 17 | |
| 394 | ||
| 395 | // Constructors that take raw pointers have a different set of "compatible" constraints | |
| 396 | // http://eel.is/c++draft/util.sharedptr#util.smartptr.shared.const-9.1 | |
| 397 | // - If T is an array type, then either T is U[N] and Y(*)[N] is convertible to T*, | |
| 398 | // or T is U[] and Y(*)[] is convertible to T*. | |
| 399 | // - If T is not an array type, then Y* is convertible to T*. | |
| 400 | #if _LIBCPP_STD_VER >= 17 | |
| 401 | template <class _Yp, class _Tp, class = void> | |
| 402 | struct __raw_pointer_compatible_with : _And< | |
| 403 | _Not<is_array<_Tp>>, | |
| 404 | is_convertible<_Yp*, _Tp*> | |
| 405 | > {}; | |
| 406 | ||
| 407 | template <class _Yp, class _Up, std::size_t _Np> | |
| 408 | struct __raw_pointer_compatible_with<_Yp, _Up[_Np], __enable_if_t< | |
| 409 | is_convertible<_Yp(*)[_Np], _Up(*)[_Np]>::value> > | |
| 410 | : true_type {}; | |
| 411 | ||
| 412 | template <class _Yp, class _Up> | |
| 413 | struct __raw_pointer_compatible_with<_Yp, _Up[], __enable_if_t< | |
| 414 | is_convertible<_Yp(*)[], _Up(*)[]>::value> > | |
| 415 | : true_type {}; | |
| 416 | ||
| 417 | #else | |
| 418 | template <class _Yp, class _Tp> | |
| 419 | struct __raw_pointer_compatible_with | |
| 420 | : is_convertible<_Yp*, _Tp*> {}; | |
| 421 | #endif // _LIBCPP_STD_VER >= 17 | |
| 422 | ||
| 377 | 423 | |
| 378 | 424 | template <class _Ptr, class = void> |
| 379 | 425 | struct __is_deletable : false_type { }; |
| ... | ... | @@ -395,12 +441,12 @@ static false_type __well_formed_deleter_test(...); |
| 395 | 441 | template <class _Dp, class _Pt> |
| 396 | 442 | struct __well_formed_deleter : decltype(std::__well_formed_deleter_test<_Dp, _Pt>(0)) {}; |
| 397 | 443 | |
| 398 | template<class _Dp, class _Tp, class _Yp> | |
| 444 | template<class _Dp, class _Yp, class _Tp> | |
| 399 | 445 | struct __shared_ptr_deleter_ctor_reqs |
| 400 | 446 | { |
| 401 | static const bool value = __compatible_with<_Tp, _Yp>::value && | |
| 447 | static const bool value = __raw_pointer_compatible_with<_Yp, _Tp>::value && | |
| 402 | 448 | is_move_constructible<_Dp>::value && |
| 403 | __well_formed_deleter<_Dp, _Tp*>::value; | |
| 449 | __well_formed_deleter<_Dp, _Yp*>::value; | |
| 404 | 450 | }; |
| 405 | 451 | |
| 406 | 452 | #if defined(_LIBCPP_ABI_ENABLE_SHARED_PTR_TRIVIAL_ABI) |
| ... | ... | @@ -439,7 +485,7 @@ public: |
| 439 | 485 | |
| 440 | 486 | template<class _Yp, class = __enable_if_t< |
| 441 | 487 | _And< |
| 442 | __compatible_with<_Yp, _Tp> | |
| 488 | __raw_pointer_compatible_with<_Yp, _Tp> | |
| 443 | 489 | // In C++03 we get errors when trying to do SFINAE with the |
| 444 | 490 | // delete operator, so we always pretend that it's deletable. |
| 445 | 491 | // The same happens on GCC. |
| ... | ... | @@ -457,7 +503,7 @@ public: |
| 457 | 503 | __enable_weak_this(__p, __p); |
| 458 | 504 | } |
| 459 | 505 | |
| 460 | template<class _Yp, class _Dp, class = __enable_if_t<__shared_ptr_deleter_ctor_reqs<_Dp, _Yp, element_type>::value> > | |
| 506 | template<class _Yp, class _Dp, class = __enable_if_t<__shared_ptr_deleter_ctor_reqs<_Dp, _Yp, _Tp>::value> > | |
| 461 | 507 | _LIBCPP_HIDE_FROM_ABI |
| 462 | 508 | shared_ptr(_Yp* __p, _Dp __d) |
| 463 | 509 | : __ptr_(__p) |
| ... | ... | @@ -484,7 +530,7 @@ public: |
| 484 | 530 | #endif // _LIBCPP_NO_EXCEPTIONS |
| 485 | 531 | } |
| 486 | 532 | |
| 487 | template<class _Yp, class _Dp, class _Alloc, class = __enable_if_t<__shared_ptr_deleter_ctor_reqs<_Dp, _Yp, element_type>::value> > | |
| 533 | template<class _Yp, class _Dp, class _Alloc, class = __enable_if_t<__shared_ptr_deleter_ctor_reqs<_Dp, _Yp, _Tp>::value> > | |
| 488 | 534 | _LIBCPP_HIDE_FROM_ABI |
| 489 | 535 | shared_ptr(_Yp* __p, _Dp __d, _Alloc __a) |
| 490 | 536 | : __ptr_(__p) |
| ... | ... | @@ -646,6 +692,7 @@ public: |
| 646 | 692 | |
| 647 | 693 | template <class _Yp, class _Dp, class = __enable_if_t< |
| 648 | 694 | !is_lvalue_reference<_Dp>::value && |
| 695 | __compatible_with<_Yp, _Tp>::value && | |
| 649 | 696 | is_convertible<typename unique_ptr<_Yp, _Dp>::pointer, element_type*>::value |
| 650 | 697 | > > |
| 651 | 698 | _LIBCPP_HIDE_FROM_ABI |
| ... | ... | @@ -668,6 +715,7 @@ public: |
| 668 | 715 | |
| 669 | 716 | template <class _Yp, class _Dp, class = void, class = __enable_if_t< |
| 670 | 717 | is_lvalue_reference<_Dp>::value && |
| 718 | __compatible_with<_Yp, _Tp>::value && | |
| 671 | 719 | is_convertible<typename unique_ptr<_Yp, _Dp>::pointer, element_type*>::value |
| 672 | 720 | > > |
| 673 | 721 | _LIBCPP_HIDE_FROM_ABI |
| ... | ... | @@ -740,9 +788,10 @@ public: |
| 740 | 788 | } |
| 741 | 789 | #endif |
| 742 | 790 | |
| 743 | template <class _Yp, class _Dp, class = __enable_if_t< | |
| 744 | is_convertible<typename unique_ptr<_Yp, _Dp>::pointer, element_type*>::value | |
| 745 | > > | |
| 791 | template <class _Yp, class _Dp, class = __enable_if_t<_And< | |
| 792 | __compatible_with<_Yp, _Tp>, | |
| 793 | is_convertible<typename unique_ptr<_Yp, _Dp>::pointer, element_type*> | |
| 794 | >::value> > | |
| 746 | 795 | _LIBCPP_HIDE_FROM_ABI |
| 747 | 796 | shared_ptr<_Tp>& operator=(unique_ptr<_Yp, _Dp>&& __r) |
| 748 | 797 | { |
| ... | ... | @@ -764,7 +813,7 @@ public: |
| 764 | 813 | } |
| 765 | 814 | |
| 766 | 815 | template<class _Yp, class = __enable_if_t< |
| 767 | __compatible_with<_Yp, _Tp>::value | |
| 816 | __raw_pointer_compatible_with<_Yp, _Tp>::value | |
| 768 | 817 | > > |
| 769 | 818 | _LIBCPP_HIDE_FROM_ABI |
| 770 | 819 | void reset(_Yp* __p) |
| ... | ... | @@ -773,8 +822,7 @@ public: |
| 773 | 822 | } |
| 774 | 823 | |
| 775 | 824 | template<class _Yp, class _Dp, class = __enable_if_t< |
| 776 | __compatible_with<_Yp, _Tp>::value | |
| 777 | > > | |
| 825 | __shared_ptr_deleter_ctor_reqs<_Dp, _Yp, _Tp>::value> > | |
| 778 | 826 | _LIBCPP_HIDE_FROM_ABI |
| 779 | 827 | void reset(_Yp* __p, _Dp __d) |
| 780 | 828 | { |
| ... | ... | @@ -782,8 +830,7 @@ public: |
| 782 | 830 | } |
| 783 | 831 | |
| 784 | 832 | template<class _Yp, class _Dp, class _Alloc, class = __enable_if_t< |
| 785 | __compatible_with<_Yp, _Tp>::value | |
| 786 | > > | |
| 833 | __shared_ptr_deleter_ctor_reqs<_Dp, _Yp, _Tp>::value> > | |
| 787 | 834 | _LIBCPP_HIDE_FROM_ABI |
| 788 | 835 | void reset(_Yp* __p, _Dp __d, _Alloc __a) |
| 789 | 836 | { |
| ... | ... | @@ -858,7 +905,7 @@ public: |
| 858 | 905 | } |
| 859 | 906 | #endif |
| 860 | 907 | |
| 861 | #ifndef _LIBCPP_NO_RTTI | |
| 908 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 862 | 909 | template <class _Dp> |
| 863 | 910 | _LIBCPP_HIDE_FROM_ABI |
| 864 | 911 | _Dp* __get_deleter() const _NOEXCEPT |
| ... | ... | @@ -867,7 +914,7 @@ public: |
| 867 | 914 | ? const_cast<void *>(__cntrl_->__get_deleter(typeid(_Dp))) |
| 868 | 915 | : nullptr); |
| 869 | 916 | } |
| 870 | #endif // _LIBCPP_NO_RTTI | |
| 917 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 871 | 918 | |
| 872 | 919 | template<class _Yp, class _CntrlBlk> |
| 873 | 920 | _LIBCPP_HIDE_FROM_ABI |
| ... | ... | @@ -963,12 +1010,9 @@ template<class _Tp, class _Alloc, __enable_if_t<!is_array<_Tp>::value, int> = 0> |
| 963 | 1010 | _LIBCPP_HIDE_FROM_ABI |
| 964 | 1011 | shared_ptr<_Tp> allocate_shared_for_overwrite(const _Alloc& __a) |
| 965 | 1012 | { |
| 966 | using _ControlBlock = __shared_ptr_emplace<_Tp, _Alloc>; | |
| 967 | using _ControlBlockAllocator = typename __allocator_traits_rebind<_Alloc, _ControlBlock>::type; | |
| 968 | __allocation_guard<_ControlBlockAllocator> __guard(__a, 1); | |
| 969 | ::new ((void*)_VSTD::addressof(*__guard.__get())) _ControlBlock(__default_initialize_tag{}, __a); | |
| 970 | auto __control_block = __guard.__release_ptr(); | |
| 971 | return shared_ptr<_Tp>::__create_with_control_block((*__control_block).__get_elem(), _VSTD::addressof(*__control_block)); | |
| 1013 | using _ForOverwriteAllocator = __allocator_traits_rebind_t<_Alloc, __for_overwrite_tag>; | |
| 1014 | _ForOverwriteAllocator __alloc(__a); | |
| 1015 | return std::allocate_shared<_Tp>(__alloc); | |
| 972 | 1016 | } |
| 973 | 1017 | |
| 974 | 1018 | template<class _Tp, __enable_if_t<!is_array<_Tp>::value, int> = 0> |
| ... | ... | @@ -1000,26 +1044,25 @@ struct __unbounded_array_control_block<_Tp[], _Alloc> : __shared_weak_count |
| 1000 | 1044 | explicit __unbounded_array_control_block(_Alloc const& __alloc, size_t __count, _Tp const& __arg) |
| 1001 | 1045 | : __alloc_(__alloc), __count_(__count) |
| 1002 | 1046 | { |
| 1003 | std::__uninitialized_allocator_fill_n(__alloc_, std::begin(__data_), __count_, __arg); | |
| 1047 | std::__uninitialized_allocator_fill_n_multidimensional(__alloc_, std::begin(__data_), __count_, __arg); | |
| 1004 | 1048 | } |
| 1005 | 1049 | |
| 1006 | 1050 | _LIBCPP_HIDE_FROM_ABI |
| 1007 | 1051 | explicit __unbounded_array_control_block(_Alloc const& __alloc, size_t __count) |
| 1008 | 1052 | : __alloc_(__alloc), __count_(__count) |
| 1009 | 1053 | { |
| 1010 | std::__uninitialized_allocator_value_construct_n(__alloc_, std::begin(__data_), __count_); | |
| 1011 | } | |
| 1012 | ||
| 1013 | 1054 | #if _LIBCPP_STD_VER >= 20 |
| 1014 | _LIBCPP_HIDE_FROM_ABI | |
| 1015 | explicit __unbounded_array_control_block(_Alloc const& __alloc, size_t __count, __default_initialize_tag) | |
| 1016 | : __alloc_(__alloc), __count_(__count) | |
| 1017 | { | |
| 1018 | // We are purposefully not using an allocator-aware default construction because the spec says so. | |
| 1019 | // There's currently no way of expressing default initialization in an allocator-aware manner anyway. | |
| 1020 | std::uninitialized_default_construct_n(std::begin(__data_), __count_); | |
| 1021 | } | |
| 1055 | if constexpr (is_same_v<typename _Alloc::value_type, __for_overwrite_tag>) { | |
| 1056 | // We are purposefully not using an allocator-aware default construction because the spec says so. | |
| 1057 | // There's currently no way of expressing default initialization in an allocator-aware manner anyway. | |
| 1058 | std::uninitialized_default_construct_n(std::begin(__data_), __count_); | |
| 1059 | } else { | |
| 1060 | std::__uninitialized_allocator_value_construct_n_multidimensional(__alloc_, std::begin(__data_), __count_); | |
| 1061 | } | |
| 1062 | #else | |
| 1063 | std::__uninitialized_allocator_value_construct_n_multidimensional(__alloc_, std::begin(__data_), __count_); | |
| 1022 | 1064 | #endif |
| 1065 | } | |
| 1023 | 1066 | |
| 1024 | 1067 | // Returns the number of bytes required to store a control block followed by the given number |
| 1025 | 1068 | // of elements of _Tp, with the whole storage being aligned to a multiple of _Tp's alignment. |
| ... | ... | @@ -1042,8 +1085,17 @@ struct __unbounded_array_control_block<_Tp[], _Alloc> : __shared_weak_count |
| 1042 | 1085 | |
| 1043 | 1086 | private: |
| 1044 | 1087 | void __on_zero_shared() _NOEXCEPT override { |
| 1088 | #if _LIBCPP_STD_VER >= 20 | |
| 1089 | if constexpr (is_same_v<typename _Alloc::value_type, __for_overwrite_tag>) { | |
| 1090 | std::__reverse_destroy(__data_, __data_ + __count_); | |
| 1091 | } else { | |
| 1092 | __allocator_traits_rebind_t<_Alloc, _Tp> __value_alloc(__alloc_); | |
| 1093 | std::__allocator_destroy_multidimensional(__value_alloc, __data_, __data_ + __count_); | |
| 1094 | } | |
| 1095 | #else | |
| 1045 | 1096 | __allocator_traits_rebind_t<_Alloc, _Tp> __value_alloc(__alloc_); |
| 1046 | 1097 | std::__allocator_destroy_multidimensional(__value_alloc, __data_, __data_ + __count_); |
| 1098 | #endif | |
| 1047 | 1099 | } |
| 1048 | 1100 | |
| 1049 | 1101 | void __on_zero_shared_weak() _NOEXCEPT override { |
| ... | ... | @@ -1096,30 +1148,40 @@ struct __bounded_array_control_block<_Tp[_Count], _Alloc> |
| 1096 | 1148 | |
| 1097 | 1149 | _LIBCPP_HIDE_FROM_ABI |
| 1098 | 1150 | explicit __bounded_array_control_block(_Alloc const& __alloc, _Tp const& __arg) : __alloc_(__alloc) { |
| 1099 | std::__uninitialized_allocator_fill_n(__alloc_, std::addressof(__data_[0]), _Count, __arg); | |
| 1151 | std::__uninitialized_allocator_fill_n_multidimensional(__alloc_, std::addressof(__data_[0]), _Count, __arg); | |
| 1100 | 1152 | } |
| 1101 | 1153 | |
| 1102 | 1154 | _LIBCPP_HIDE_FROM_ABI |
| 1103 | 1155 | explicit __bounded_array_control_block(_Alloc const& __alloc) : __alloc_(__alloc) { |
| 1104 | std::__uninitialized_allocator_value_construct_n(__alloc_, std::addressof(__data_[0]), _Count); | |
| 1105 | } | |
| 1106 | ||
| 1107 | 1156 | #if _LIBCPP_STD_VER >= 20 |
| 1108 | _LIBCPP_HIDE_FROM_ABI | |
| 1109 | explicit __bounded_array_control_block(_Alloc const& __alloc, __default_initialize_tag) : __alloc_(__alloc) { | |
| 1110 | // We are purposefully not using an allocator-aware default construction because the spec says so. | |
| 1111 | // There's currently no way of expressing default initialization in an allocator-aware manner anyway. | |
| 1112 | std::uninitialized_default_construct_n(std::addressof(__data_[0]), _Count); | |
| 1113 | } | |
| 1157 | if constexpr (is_same_v<typename _Alloc::value_type, __for_overwrite_tag>) { | |
| 1158 | // We are purposefully not using an allocator-aware default construction because the spec says so. | |
| 1159 | // There's currently no way of expressing default initialization in an allocator-aware manner anyway. | |
| 1160 | std::uninitialized_default_construct_n(std::addressof(__data_[0]), _Count); | |
| 1161 | } else { | |
| 1162 | std::__uninitialized_allocator_value_construct_n_multidimensional(__alloc_, std::addressof(__data_[0]), _Count); | |
| 1163 | } | |
| 1164 | #else | |
| 1165 | std::__uninitialized_allocator_value_construct_n_multidimensional(__alloc_, std::addressof(__data_[0]), _Count); | |
| 1114 | 1166 | #endif |
| 1167 | } | |
| 1115 | 1168 | |
| 1116 | 1169 | _LIBCPP_HIDE_FROM_ABI_VIRTUAL |
| 1117 | 1170 | ~__bounded_array_control_block() override { } // can't be `= default` because of the sometimes-non-trivial union member __data_ |
| 1118 | 1171 | |
| 1119 | 1172 | private: |
| 1120 | 1173 | void __on_zero_shared() _NOEXCEPT override { |
| 1174 | #if _LIBCPP_STD_VER >= 20 | |
| 1175 | if constexpr (is_same_v<typename _Alloc::value_type, __for_overwrite_tag>) { | |
| 1176 | std::__reverse_destroy(__data_, __data_ + _Count); | |
| 1177 | } else { | |
| 1178 | __allocator_traits_rebind_t<_Alloc, _Tp> __value_alloc(__alloc_); | |
| 1179 | std::__allocator_destroy_multidimensional(__value_alloc, __data_, __data_ + _Count); | |
| 1180 | } | |
| 1181 | #else | |
| 1121 | 1182 | __allocator_traits_rebind_t<_Alloc, _Tp> __value_alloc(__alloc_); |
| 1122 | 1183 | std::__allocator_destroy_multidimensional(__value_alloc, __data_, __data_ + _Count); |
| 1184 | #endif | |
| 1123 | 1185 | } |
| 1124 | 1186 | |
| 1125 | 1187 | void __on_zero_shared_weak() _NOEXCEPT override { |
| ... | ... | @@ -1175,7 +1237,9 @@ template<class _Tp, class _Alloc, __enable_if_t<is_bounded_array<_Tp>::value, in |
| 1175 | 1237 | _LIBCPP_HIDE_FROM_ABI |
| 1176 | 1238 | shared_ptr<_Tp> allocate_shared_for_overwrite(const _Alloc& __a) |
| 1177 | 1239 | { |
| 1178 | return std::__allocate_shared_bounded_array<_Tp>(__a, __default_initialize_tag{}); | |
| 1240 | using _ForOverwriteAllocator = __allocator_traits_rebind_t<_Alloc, __for_overwrite_tag>; | |
| 1241 | _ForOverwriteAllocator __alloc(__a); | |
| 1242 | return std::__allocate_shared_bounded_array<_Tp>(__alloc); | |
| 1179 | 1243 | } |
| 1180 | 1244 | |
| 1181 | 1245 | template<class _Tp, class = __enable_if_t<is_bounded_array<_Tp>::value>> |
| ... | ... | @@ -1196,7 +1260,7 @@ template<class _Tp, __enable_if_t<is_bounded_array<_Tp>::value, int> = 0> |
| 1196 | 1260 | _LIBCPP_HIDE_FROM_ABI |
| 1197 | 1261 | shared_ptr<_Tp> make_shared_for_overwrite() |
| 1198 | 1262 | { |
| 1199 | return std::__allocate_shared_bounded_array<_Tp>(allocator<_Tp>(), __default_initialize_tag{}); | |
| 1263 | return std::__allocate_shared_bounded_array<_Tp>(allocator<__for_overwrite_tag>()); | |
| 1200 | 1264 | } |
| 1201 | 1265 | |
| 1202 | 1266 | // unbounded array variants |
| ... | ... | @@ -1218,7 +1282,9 @@ template<class _Tp, class _Alloc, __enable_if_t<is_unbounded_array<_Tp>::value, |
| 1218 | 1282 | _LIBCPP_HIDE_FROM_ABI |
| 1219 | 1283 | shared_ptr<_Tp> allocate_shared_for_overwrite(const _Alloc& __a, size_t __n) |
| 1220 | 1284 | { |
| 1221 | return std::__allocate_shared_unbounded_array<_Tp>(__a, __n, __default_initialize_tag{}); | |
| 1285 | using _ForOverwriteAllocator = __allocator_traits_rebind_t<_Alloc, __for_overwrite_tag>; | |
| 1286 | _ForOverwriteAllocator __alloc(__a); | |
| 1287 | return std::__allocate_shared_unbounded_array<_Tp>(__alloc, __n); | |
| 1222 | 1288 | } |
| 1223 | 1289 | |
| 1224 | 1290 | template<class _Tp, class = __enable_if_t<is_unbounded_array<_Tp>::value>> |
| ... | ... | @@ -1239,7 +1305,7 @@ template<class _Tp, __enable_if_t<is_unbounded_array<_Tp>::value, int> = 0> |
| 1239 | 1305 | _LIBCPP_HIDE_FROM_ABI |
| 1240 | 1306 | shared_ptr<_Tp> make_shared_for_overwrite(size_t __n) |
| 1241 | 1307 | { |
| 1242 | return std::__allocate_shared_unbounded_array<_Tp>(allocator<_Tp>(), __n, __default_initialize_tag{}); | |
| 1308 | return std::__allocate_shared_unbounded_array<_Tp>(allocator<__for_overwrite_tag>(), __n); | |
| 1243 | 1309 | } |
| 1244 | 1310 | |
| 1245 | 1311 | #endif // _LIBCPP_STD_VER > 17 |
| ... | ... | @@ -1465,7 +1531,7 @@ reinterpret_pointer_cast(const shared_ptr<_Up>& __r) _NOEXCEPT |
| 1465 | 1531 | typename shared_ptr<_Tp>::element_type*>(__r.get())); |
| 1466 | 1532 | } |
| 1467 | 1533 | |
| 1468 | #ifndef _LIBCPP_NO_RTTI | |
| 1534 | #ifndef _LIBCPP_HAS_NO_RTTI | |
| 1469 | 1535 | |
| 1470 | 1536 | template<class _Dp, class _Tp> |
| 1471 | 1537 | inline _LIBCPP_INLINE_VISIBILITY |
| ... | ... | @@ -1475,7 +1541,7 @@ get_deleter(const shared_ptr<_Tp>& __p) _NOEXCEPT |
| 1475 | 1541 | return __p.template __get_deleter<_Dp>(); |
| 1476 | 1542 | } |
| 1477 | 1543 | |
| 1478 | #endif // _LIBCPP_NO_RTTI | |
| 1544 | #endif // _LIBCPP_HAS_NO_RTTI | |
| 1479 | 1545 | |
| 1480 | 1546 | template<class _Tp> |
| 1481 | 1547 | class _LIBCPP_SHARED_PTR_TRIVIAL_ABI _LIBCPP_TEMPLATE_VIS weak_ptr |
lib/libcxx/include/__memory/uninitialized_algorithms.h+13-13| ... | ... | @@ -410,7 +410,7 @@ constexpr void __allocator_destroy_multidimensional(_Alloc& __alloc, _BidirIter |
| 410 | 410 | // This function assumes that the allocator is bound to the correct type. |
| 411 | 411 | template<class _Alloc, class _Tp> |
| 412 | 412 | _LIBCPP_HIDE_FROM_ABI |
| 413 | constexpr void __allocator_construct_at(_Alloc& __alloc, _Tp* __loc) { | |
| 413 | constexpr void __allocator_construct_at_multidimensional(_Alloc& __alloc, _Tp* __loc) { | |
| 414 | 414 | static_assert(is_same_v<typename allocator_traits<_Alloc>::value_type, _Tp>, |
| 415 | 415 | "The allocator should already be rebound to the correct type"); |
| 416 | 416 | |
| ... | ... | @@ -426,7 +426,7 @@ constexpr void __allocator_construct_at(_Alloc& __alloc, _Tp* __loc) { |
| 426 | 426 | }); |
| 427 | 427 | |
| 428 | 428 | for (; __i != extent_v<_Tp>; ++__i) { |
| 429 | std::__allocator_construct_at(__elem_alloc, std::addressof(__array[__i])); | |
| 429 | std::__allocator_construct_at_multidimensional(__elem_alloc, std::addressof(__array[__i])); | |
| 430 | 430 | } |
| 431 | 431 | __guard.__complete(); |
| 432 | 432 | } else { |
| ... | ... | @@ -446,13 +446,13 @@ constexpr void __allocator_construct_at(_Alloc& __alloc, _Tp* __loc) { |
| 446 | 446 | // This function assumes that the allocator is bound to the correct type. |
| 447 | 447 | template<class _Alloc, class _Tp, class _Arg> |
| 448 | 448 | _LIBCPP_HIDE_FROM_ABI |
| 449 | constexpr void __allocator_construct_at(_Alloc& __alloc, _Tp* __loc, _Arg const& __arg) { | |
| 449 | constexpr void __allocator_construct_at_multidimensional(_Alloc& __alloc, _Tp* __loc, _Arg const& __arg) { | |
| 450 | 450 | static_assert(is_same_v<typename allocator_traits<_Alloc>::value_type, _Tp>, |
| 451 | 451 | "The allocator should already be rebound to the correct type"); |
| 452 | 452 | |
| 453 | 453 | if constexpr (is_array_v<_Tp>) { |
| 454 | 454 | static_assert(is_array_v<_Arg>, |
| 455 | "Provided non-array initialization argument to __allocator_construct_at when " | |
| 455 | "Provided non-array initialization argument to __allocator_construct_at_multidimensional when " | |
| 456 | 456 | "trying to construct an array."); |
| 457 | 457 | |
| 458 | 458 | using _Element = remove_extent_t<_Tp>; |
| ... | ... | @@ -465,7 +465,7 @@ constexpr void __allocator_construct_at(_Alloc& __alloc, _Tp* __loc, _Arg const& |
| 465 | 465 | std::__allocator_destroy_multidimensional(__elem_alloc, __array, __array + __i); |
| 466 | 466 | }); |
| 467 | 467 | for (; __i != extent_v<_Tp>; ++__i) { |
| 468 | std::__allocator_construct_at(__elem_alloc, std::addressof(__array[__i]), __arg[__i]); | |
| 468 | std::__allocator_construct_at_multidimensional(__elem_alloc, std::addressof(__array[__i]), __arg[__i]); | |
| 469 | 469 | } |
| 470 | 470 | __guard.__complete(); |
| 471 | 471 | } else { |
| ... | ... | @@ -481,8 +481,8 @@ constexpr void __allocator_construct_at(_Alloc& __alloc, _Tp* __loc, _Arg const& |
| 481 | 481 | // initialization using allocator_traits destruction. If the elements in the range are C-style |
| 482 | 482 | // arrays, they are initialized element-wise using allocator construction, and recursively so. |
| 483 | 483 | template<class _Alloc, class _BidirIter, class _Tp, class _Size = typename iterator_traits<_BidirIter>::difference_type> |
| 484 | _LIBCPP_HIDE_FROM_ABI | |
| 485 | constexpr void __uninitialized_allocator_fill_n(_Alloc& __alloc, _BidirIter __it, _Size __n, _Tp const& __value) { | |
| 484 | _LIBCPP_HIDE_FROM_ABI constexpr void | |
| 485 | __uninitialized_allocator_fill_n_multidimensional(_Alloc& __alloc, _BidirIter __it, _Size __n, _Tp const& __value) { | |
| 486 | 486 | using _ValueType = typename iterator_traits<_BidirIter>::value_type; |
| 487 | 487 | __allocator_traits_rebind_t<_Alloc, _ValueType> __value_alloc(__alloc); |
| 488 | 488 | _BidirIter __begin = __it; |
| ... | ... | @@ -490,16 +490,16 @@ constexpr void __uninitialized_allocator_fill_n(_Alloc& __alloc, _BidirIter __it |
| 490 | 490 | // If an exception is thrown, destroy what we have constructed so far in reverse order. |
| 491 | 491 | __exception_guard __guard([&]() { std::__allocator_destroy_multidimensional(__value_alloc, __begin, __it); }); |
| 492 | 492 | for (; __n != 0; --__n, ++__it) { |
| 493 | std::__allocator_construct_at(__value_alloc, std::addressof(*__it), __value); | |
| 493 | std::__allocator_construct_at_multidimensional(__value_alloc, std::addressof(*__it), __value); | |
| 494 | 494 | } |
| 495 | 495 | __guard.__complete(); |
| 496 | 496 | } |
| 497 | 497 | |
| 498 | // Same as __uninitialized_allocator_fill_n, but doesn't pass any initialization argument | |
| 498 | // Same as __uninitialized_allocator_fill_n_multidimensional, but doesn't pass any initialization argument | |
| 499 | 499 | // to the allocator's construct method, which results in value initialization. |
| 500 | template<class _Alloc, class _BidirIter, class _Size = typename iterator_traits<_BidirIter>::difference_type> | |
| 501 | _LIBCPP_HIDE_FROM_ABI | |
| 502 | constexpr void __uninitialized_allocator_value_construct_n(_Alloc& __alloc, _BidirIter __it, _Size __n) { | |
| 500 | template <class _Alloc, class _BidirIter, class _Size = typename iterator_traits<_BidirIter>::difference_type> | |
| 501 | _LIBCPP_HIDE_FROM_ABI constexpr void | |
| 502 | __uninitialized_allocator_value_construct_n_multidimensional(_Alloc& __alloc, _BidirIter __it, _Size __n) { | |
| 503 | 503 | using _ValueType = typename iterator_traits<_BidirIter>::value_type; |
| 504 | 504 | __allocator_traits_rebind_t<_Alloc, _ValueType> __value_alloc(__alloc); |
| 505 | 505 | _BidirIter __begin = __it; |
| ... | ... | @@ -507,7 +507,7 @@ constexpr void __uninitialized_allocator_value_construct_n(_Alloc& __alloc, _Bid |
| 507 | 507 | // If an exception is thrown, destroy what we have constructed so far in reverse order. |
| 508 | 508 | __exception_guard __guard([&]() { std::__allocator_destroy_multidimensional(__value_alloc, __begin, __it); }); |
| 509 | 509 | for (; __n != 0; --__n, ++__it) { |
| 510 | std::__allocator_construct_at(__value_alloc, std::addressof(*__it)); | |
| 510 | std::__allocator_construct_at_multidimensional(__value_alloc, std::addressof(*__it)); | |
| 511 | 511 | } |
| 512 | 512 | __guard.__complete(); |
| 513 | 513 | } |
lib/libcxx/include/__ranges/elements_view.h+54-64| ... | ... | @@ -49,12 +49,6 @@ _LIBCPP_BEGIN_NAMESPACE_STD |
| 49 | 49 | |
| 50 | 50 | namespace ranges { |
| 51 | 51 | |
| 52 | template <class _View, size_t _Np, bool _Const> | |
| 53 | class __elements_view_iterator; | |
| 54 | ||
| 55 | template <class _View, size_t _Np, bool _Const> | |
| 56 | class __elements_view_sentinel; | |
| 57 | ||
| 58 | 52 | template <class _Tp, size_t _Np> |
| 59 | 53 | concept __has_tuple_element = __tuple_like<_Tp> && _Np < tuple_size<_Tp>::value; |
| 60 | 54 | |
| ... | ... | @@ -66,6 +60,13 @@ template <input_range _View, size_t _Np> |
| 66 | 60 | __has_tuple_element<remove_reference_t<range_reference_t<_View>>, _Np> && |
| 67 | 61 | __returnable_element<range_reference_t<_View>, _Np> |
| 68 | 62 | class elements_view : public view_interface<elements_view<_View, _Np>> { |
| 63 | private: | |
| 64 | template <bool> | |
| 65 | class __iterator; | |
| 66 | ||
| 67 | template <bool> | |
| 68 | class __sentinel; | |
| 69 | ||
| 69 | 70 | public: |
| 70 | 71 | _LIBCPP_HIDE_FROM_ABI elements_view() |
| 71 | 72 | requires default_initializable<_View> |
| ... | ... | @@ -130,12 +131,6 @@ public: |
| 130 | 131 | } |
| 131 | 132 | |
| 132 | 133 | private: |
| 133 | template <bool _Const> | |
| 134 | using __iterator = __elements_view_iterator<_View, _Np, _Const>; | |
| 135 | ||
| 136 | template <bool _Const> | |
| 137 | using __sentinel = __elements_view_sentinel<_View, _Np, _Const>; | |
| 138 | ||
| 139 | 134 | _LIBCPP_NO_UNIQUE_ADDRESS _View __base_ = _View(); |
| 140 | 135 | }; |
| 141 | 136 | |
| ... | ... | @@ -160,13 +155,18 @@ struct __elements_view_iterator_category_base<_Base, _Np> { |
| 160 | 155 | using iterator_category = decltype(__get_iterator_category()); |
| 161 | 156 | }; |
| 162 | 157 | |
| 163 | template <class _View, size_t _Np, bool _Const> | |
| 164 | class __elements_view_iterator : public __elements_view_iterator_category_base<__maybe_const<_Const, _View>, _Np> { | |
| 165 | template <class, size_t, bool > | |
| 166 | friend class __elements_view_iterator; | |
| 158 | template <input_range _View, size_t _Np> | |
| 159 | requires view<_View> && __has_tuple_element<range_value_t<_View>, _Np> && | |
| 160 | __has_tuple_element<remove_reference_t<range_reference_t<_View>>, _Np> && | |
| 161 | __returnable_element<range_reference_t<_View>, _Np> | |
| 162 | template <bool _Const> | |
| 163 | class elements_view<_View, _Np>::__iterator | |
| 164 | : public __elements_view_iterator_category_base<__maybe_const<_Const, _View>, _Np> { | |
| 165 | template <bool> | |
| 166 | friend class __iterator; | |
| 167 | 167 | |
| 168 | template <class, size_t, bool > | |
| 169 | friend class __elements_view_sentinel; | |
| 168 | template <bool> | |
| 169 | friend class __sentinel; | |
| 170 | 170 | |
| 171 | 171 | using _Base = __maybe_const<_Const, _View>; |
| 172 | 172 | |
| ... | ... | @@ -198,14 +198,13 @@ public: |
| 198 | 198 | using value_type = remove_cvref_t<tuple_element_t<_Np, range_value_t<_Base>>>; |
| 199 | 199 | using difference_type = range_difference_t<_Base>; |
| 200 | 200 | |
| 201 | _LIBCPP_HIDE_FROM_ABI __elements_view_iterator() | |
| 201 | _LIBCPP_HIDE_FROM_ABI __iterator() | |
| 202 | 202 | requires default_initializable<iterator_t<_Base>> |
| 203 | 203 | = default; |
| 204 | 204 | |
| 205 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __elements_view_iterator(iterator_t<_Base> __current) | |
| 206 | : __current_(std::move(__current)) {} | |
| 205 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __iterator(iterator_t<_Base> __current) : __current_(std::move(__current)) {} | |
| 207 | 206 | |
| 208 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_iterator(__elements_view_iterator<_View, _Np, !_Const> __i) | |
| 207 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator(__iterator<!_Const> __i) | |
| 209 | 208 | requires _Const && convertible_to<iterator_t<_View>, iterator_t<_Base>> |
| 210 | 209 | : __current_(std::move(__i.__current_)) {} |
| 211 | 210 | |
| ... | ... | @@ -215,14 +214,14 @@ public: |
| 215 | 214 | |
| 216 | 215 | _LIBCPP_HIDE_FROM_ABI constexpr decltype(auto) operator*() const { return __get_element(__current_); } |
| 217 | 216 | |
| 218 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_iterator& operator++() { | |
| 217 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator& operator++() { | |
| 219 | 218 | ++__current_; |
| 220 | 219 | return *this; |
| 221 | 220 | } |
| 222 | 221 | |
| 223 | 222 | _LIBCPP_HIDE_FROM_ABI constexpr void operator++(int) { ++__current_; } |
| 224 | 223 | |
| 225 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_iterator operator++(int) | |
| 224 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator operator++(int) | |
| 226 | 225 | requires forward_range<_Base> |
| 227 | 226 | { |
| 228 | 227 | auto temp = *this; |
| ... | ... | @@ -230,14 +229,14 @@ public: |
| 230 | 229 | return temp; |
| 231 | 230 | } |
| 232 | 231 | |
| 233 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_iterator& operator--() | |
| 232 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator& operator--() | |
| 234 | 233 | requires bidirectional_range<_Base> |
| 235 | 234 | { |
| 236 | 235 | --__current_; |
| 237 | 236 | return *this; |
| 238 | 237 | } |
| 239 | 238 | |
| 240 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_iterator operator--(int) | |
| 239 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator operator--(int) | |
| 241 | 240 | requires bidirectional_range<_Base> |
| 242 | 241 | { |
| 243 | 242 | auto temp = *this; |
| ... | ... | @@ -245,14 +244,14 @@ public: |
| 245 | 244 | return temp; |
| 246 | 245 | } |
| 247 | 246 | |
| 248 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_iterator& operator+=(difference_type __n) | |
| 247 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator& operator+=(difference_type __n) | |
| 249 | 248 | requires random_access_range<_Base> |
| 250 | 249 | { |
| 251 | 250 | __current_ += __n; |
| 252 | 251 | return *this; |
| 253 | 252 | } |
| 254 | 253 | |
| 255 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_iterator& operator-=(difference_type __n) | |
| 254 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator& operator-=(difference_type __n) | |
| 256 | 255 | requires random_access_range<_Base> |
| 257 | 256 | { |
| 258 | 257 | __current_ -= __n; |
| ... | ... | @@ -265,99 +264,91 @@ public: |
| 265 | 264 | return __get_element(__current_ + __n); |
| 266 | 265 | } |
| 267 | 266 | |
| 268 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 269 | operator==(const __elements_view_iterator& __x, const __elements_view_iterator& __y) | |
| 267 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator==(const __iterator& __x, const __iterator& __y) | |
| 270 | 268 | requires equality_comparable<iterator_t<_Base>> |
| 271 | 269 | { |
| 272 | 270 | return __x.__current_ == __y.__current_; |
| 273 | 271 | } |
| 274 | 272 | |
| 275 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 276 | operator<(const __elements_view_iterator& __x, const __elements_view_iterator& __y) | |
| 273 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator<(const __iterator& __x, const __iterator& __y) | |
| 277 | 274 | requires random_access_range<_Base> |
| 278 | 275 | { |
| 279 | 276 | return __x.__current_ < __y.__current_; |
| 280 | 277 | } |
| 281 | 278 | |
| 282 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 283 | operator>(const __elements_view_iterator& __x, const __elements_view_iterator& __y) | |
| 279 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator>(const __iterator& __x, const __iterator& __y) | |
| 284 | 280 | requires random_access_range<_Base> |
| 285 | 281 | { |
| 286 | 282 | return __y < __x; |
| 287 | 283 | } |
| 288 | 284 | |
| 289 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 290 | operator<=(const __elements_view_iterator& __x, const __elements_view_iterator& __y) | |
| 285 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator<=(const __iterator& __x, const __iterator& __y) | |
| 291 | 286 | requires random_access_range<_Base> |
| 292 | 287 | { |
| 293 | 288 | return !(__y < __x); |
| 294 | 289 | } |
| 295 | 290 | |
| 296 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 297 | operator>=(const __elements_view_iterator& __x, const __elements_view_iterator& __y) | |
| 291 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator>=(const __iterator& __x, const __iterator& __y) | |
| 298 | 292 | requires random_access_range<_Base> |
| 299 | 293 | { |
| 300 | 294 | return !(__x < __y); |
| 301 | 295 | } |
| 302 | 296 | |
| 303 | _LIBCPP_HIDE_FROM_ABI friend constexpr auto | |
| 304 | operator<=>(const __elements_view_iterator& __x, const __elements_view_iterator& __y) | |
| 297 | _LIBCPP_HIDE_FROM_ABI friend constexpr auto operator<=>(const __iterator& __x, const __iterator& __y) | |
| 305 | 298 | requires random_access_range<_Base> && three_way_comparable<iterator_t<_Base>> |
| 306 | 299 | { |
| 307 | 300 | return __x.__current_ <=> __y.__current_; |
| 308 | 301 | } |
| 309 | 302 | |
| 310 | _LIBCPP_HIDE_FROM_ABI friend constexpr __elements_view_iterator | |
| 311 | operator+(const __elements_view_iterator& __x, difference_type __y) | |
| 303 | _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator+(const __iterator& __x, difference_type __y) | |
| 312 | 304 | requires random_access_range<_Base> |
| 313 | 305 | { |
| 314 | return __elements_view_iterator{__x} += __y; | |
| 306 | return __iterator{__x} += __y; | |
| 315 | 307 | } |
| 316 | 308 | |
| 317 | _LIBCPP_HIDE_FROM_ABI friend constexpr __elements_view_iterator | |
| 318 | operator+(difference_type __x, const __elements_view_iterator& __y) | |
| 309 | _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator+(difference_type __x, const __iterator& __y) | |
| 319 | 310 | requires random_access_range<_Base> |
| 320 | 311 | { |
| 321 | 312 | return __y + __x; |
| 322 | 313 | } |
| 323 | 314 | |
| 324 | _LIBCPP_HIDE_FROM_ABI friend constexpr __elements_view_iterator | |
| 325 | operator-(const __elements_view_iterator& __x, difference_type __y) | |
| 315 | _LIBCPP_HIDE_FROM_ABI friend constexpr __iterator operator-(const __iterator& __x, difference_type __y) | |
| 326 | 316 | requires random_access_range<_Base> |
| 327 | 317 | { |
| 328 | return __elements_view_iterator{__x} -= __y; | |
| 318 | return __iterator{__x} -= __y; | |
| 329 | 319 | } |
| 330 | 320 | |
| 331 | _LIBCPP_HIDE_FROM_ABI friend constexpr difference_type | |
| 332 | operator-(const __elements_view_iterator& __x, const __elements_view_iterator& __y) | |
| 321 | _LIBCPP_HIDE_FROM_ABI friend constexpr difference_type operator-(const __iterator& __x, const __iterator& __y) | |
| 333 | 322 | requires sized_sentinel_for<iterator_t<_Base>, iterator_t<_Base>> |
| 334 | 323 | { |
| 335 | 324 | return __x.__current_ - __y.__current_; |
| 336 | 325 | } |
| 337 | 326 | }; |
| 338 | 327 | |
| 339 | template <class _View, size_t _Np, bool _Const> | |
| 340 | class __elements_view_sentinel { | |
| 328 | template <input_range _View, size_t _Np> | |
| 329 | requires view<_View> && __has_tuple_element<range_value_t<_View>, _Np> && | |
| 330 | __has_tuple_element<remove_reference_t<range_reference_t<_View>>, _Np> && | |
| 331 | __returnable_element<range_reference_t<_View>, _Np> | |
| 332 | template <bool _Const> | |
| 333 | class elements_view<_View, _Np>::__sentinel { | |
| 341 | 334 | private: |
| 342 | 335 | using _Base = __maybe_const<_Const, _View>; |
| 343 | 336 | _LIBCPP_NO_UNIQUE_ADDRESS sentinel_t<_Base> __end_ = sentinel_t<_Base>(); |
| 344 | 337 | |
| 345 | template <class, size_t, bool > | |
| 346 | friend class __elements_view_sentinel; | |
| 338 | template <bool> | |
| 339 | friend class __sentinel; | |
| 347 | 340 | |
| 348 | 341 | template <bool _AnyConst> |
| 349 | _LIBCPP_HIDE_FROM_ABI static constexpr decltype(auto) | |
| 350 | __get_current(const __elements_view_iterator<_View, _Np, _AnyConst>& __iter) { | |
| 342 | _LIBCPP_HIDE_FROM_ABI static constexpr decltype(auto) __get_current(const __iterator<_AnyConst>& __iter) { | |
| 351 | 343 | return (__iter.__current_); |
| 352 | 344 | } |
| 353 | 345 | |
| 354 | 346 | public: |
| 355 | _LIBCPP_HIDE_FROM_ABI __elements_view_sentinel() = default; | |
| 347 | _LIBCPP_HIDE_FROM_ABI __sentinel() = default; | |
| 356 | 348 | |
| 357 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __elements_view_sentinel(sentinel_t<_Base> __end) | |
| 358 | : __end_(std::move(__end)) {} | |
| 349 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __sentinel(sentinel_t<_Base> __end) : __end_(std::move(__end)) {} | |
| 359 | 350 | |
| 360 | _LIBCPP_HIDE_FROM_ABI constexpr __elements_view_sentinel(__elements_view_sentinel<_View, _Np, !_Const> __other) | |
| 351 | _LIBCPP_HIDE_FROM_ABI constexpr __sentinel(__sentinel<!_Const> __other) | |
| 361 | 352 | requires _Const && convertible_to<sentinel_t<_View>, sentinel_t<_Base>> |
| 362 | 353 | : __end_(std::move(__other.__end_)) {} |
| 363 | 354 | |
| ... | ... | @@ -365,22 +356,21 @@ public: |
| 365 | 356 | |
| 366 | 357 | template <bool _OtherConst> |
| 367 | 358 | requires sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 368 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 369 | operator==(const __elements_view_iterator<_View, _Np, _OtherConst>& __x, const __elements_view_sentinel& __y) { | |
| 359 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator==(const __iterator<_OtherConst>& __x, const __sentinel& __y) { | |
| 370 | 360 | return __get_current(__x) == __y.__end_; |
| 371 | 361 | } |
| 372 | 362 | |
| 373 | 363 | template <bool _OtherConst> |
| 374 | 364 | requires sized_sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 375 | 365 | _LIBCPP_HIDE_FROM_ABI friend constexpr range_difference_t<__maybe_const<_OtherConst, _View>> |
| 376 | operator-(const __elements_view_iterator<_View, _Np, _OtherConst>& __x, const __elements_view_sentinel& __y) { | |
| 366 | operator-(const __iterator<_OtherConst>& __x, const __sentinel& __y) { | |
| 377 | 367 | return __get_current(__x) - __y.__end_; |
| 378 | 368 | } |
| 379 | 369 | |
| 380 | 370 | template <bool _OtherConst> |
| 381 | 371 | requires sized_sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 382 | 372 | _LIBCPP_HIDE_FROM_ABI friend constexpr range_difference_t<__maybe_const<_OtherConst, _View>> |
| 383 | operator-(const __elements_view_sentinel& __x, const __elements_view_iterator<_View, _Np, _OtherConst>& __y) { | |
| 373 | operator-(const __sentinel& __x, const __iterator<_OtherConst>& __y) { | |
| 384 | 374 | return __x.__end_ - __get_current(__y); |
| 385 | 375 | } |
| 386 | 376 | }; |
lib/libcxx/include/__ranges/filter_view.h+17-33| ... | ... | @@ -46,15 +46,6 @@ _LIBCPP_BEGIN_NAMESPACE_STD |
| 46 | 46 | #if _LIBCPP_STD_VER > 17 |
| 47 | 47 | |
| 48 | 48 | namespace ranges { |
| 49 | ||
| 50 | template <input_range _View, indirect_unary_predicate<iterator_t<_View>> _Pred> | |
| 51 | requires view<_View> && is_object_v<_Pred> | |
| 52 | class __filter_view_iterator; | |
| 53 | ||
| 54 | template <input_range _View, indirect_unary_predicate<iterator_t<_View>> _Pred> | |
| 55 | requires view<_View> && is_object_v<_Pred> | |
| 56 | class __filter_view_sentinel; | |
| 57 | ||
| 58 | 49 | template<input_range _View, indirect_unary_predicate<iterator_t<_View>> _Pred> |
| 59 | 50 | requires view<_View> && is_object_v<_Pred> |
| 60 | 51 | class filter_view : public view_interface<filter_view<_View, _Pred>> { |
| ... | ... | @@ -67,11 +58,8 @@ namespace ranges { |
| 67 | 58 | using _Cache = _If<_UseCache, __non_propagating_cache<iterator_t<_View>>, __empty_cache>; |
| 68 | 59 | _LIBCPP_NO_UNIQUE_ADDRESS _Cache __cached_begin_ = _Cache(); |
| 69 | 60 | |
| 70 | using __iterator = __filter_view_iterator<_View, _Pred>; | |
| 71 | using __sentinel = __filter_view_sentinel<_View, _Pred>; | |
| 72 | ||
| 73 | friend __iterator; | |
| 74 | friend __sentinel; | |
| 61 | class __iterator; | |
| 62 | class __sentinel; | |
| 75 | 63 | |
| 76 | 64 | public: |
| 77 | 65 | _LIBCPP_HIDE_FROM_ABI |
| ... | ... | @@ -131,13 +119,11 @@ namespace ranges { |
| 131 | 119 | |
| 132 | 120 | template<input_range _View, indirect_unary_predicate<iterator_t<_View>> _Pred> |
| 133 | 121 | requires view<_View> && is_object_v<_Pred> |
| 134 | class __filter_view_iterator : public __filter_iterator_category<_View> { | |
| 135 | ||
| 136 | using __filter_view = filter_view<_View, _Pred>; | |
| 122 | class filter_view<_View, _Pred>::__iterator : public __filter_iterator_category<_View> { | |
| 137 | 123 | |
| 138 | 124 | public: |
| 139 | 125 | _LIBCPP_NO_UNIQUE_ADDRESS iterator_t<_View> __current_ = iterator_t<_View>(); |
| 140 | _LIBCPP_NO_UNIQUE_ADDRESS __filter_view* __parent_ = nullptr; | |
| 126 | _LIBCPP_NO_UNIQUE_ADDRESS filter_view* __parent_ = nullptr; | |
| 141 | 127 | |
| 142 | 128 | using iterator_concept = |
| 143 | 129 | _If<bidirectional_range<_View>, bidirectional_iterator_tag, |
| ... | ... | @@ -149,10 +135,10 @@ namespace ranges { |
| 149 | 135 | using difference_type = range_difference_t<_View>; |
| 150 | 136 | |
| 151 | 137 | _LIBCPP_HIDE_FROM_ABI |
| 152 | __filter_view_iterator() requires default_initializable<iterator_t<_View>> = default; | |
| 138 | __iterator() requires default_initializable<iterator_t<_View>> = default; | |
| 153 | 139 | |
| 154 | 140 | _LIBCPP_HIDE_FROM_ABI |
| 155 | constexpr __filter_view_iterator(__filter_view& __parent, iterator_t<_View> __current) | |
| 141 | constexpr __iterator(filter_view& __parent, iterator_t<_View> __current) | |
| 156 | 142 | : __current_(std::move(__current)), __parent_(std::addressof(__parent)) |
| 157 | 143 | { } |
| 158 | 144 | |
| ... | ... | @@ -171,7 +157,7 @@ namespace ranges { |
| 171 | 157 | } |
| 172 | 158 | |
| 173 | 159 | _LIBCPP_HIDE_FROM_ABI |
| 174 | constexpr __filter_view_iterator& operator++() { | |
| 160 | constexpr __iterator& operator++() { | |
| 175 | 161 | __current_ = ranges::find_if(std::move(++__current_), ranges::end(__parent_->__base_), |
| 176 | 162 | std::ref(*__parent_->__pred_)); |
| 177 | 163 | return *this; |
| ... | ... | @@ -179,42 +165,42 @@ namespace ranges { |
| 179 | 165 | _LIBCPP_HIDE_FROM_ABI |
| 180 | 166 | constexpr void operator++(int) { ++*this; } |
| 181 | 167 | _LIBCPP_HIDE_FROM_ABI |
| 182 | constexpr __filter_view_iterator operator++(int) requires forward_range<_View> { | |
| 168 | constexpr __iterator operator++(int) requires forward_range<_View> { | |
| 183 | 169 | auto __tmp = *this; |
| 184 | 170 | ++*this; |
| 185 | 171 | return __tmp; |
| 186 | 172 | } |
| 187 | 173 | |
| 188 | 174 | _LIBCPP_HIDE_FROM_ABI |
| 189 | constexpr __filter_view_iterator& operator--() requires bidirectional_range<_View> { | |
| 175 | constexpr __iterator& operator--() requires bidirectional_range<_View> { | |
| 190 | 176 | do { |
| 191 | 177 | --__current_; |
| 192 | 178 | } while (!std::invoke(*__parent_->__pred_, *__current_)); |
| 193 | 179 | return *this; |
| 194 | 180 | } |
| 195 | 181 | _LIBCPP_HIDE_FROM_ABI |
| 196 | constexpr __filter_view_iterator operator--(int) requires bidirectional_range<_View> { | |
| 182 | constexpr __iterator operator--(int) requires bidirectional_range<_View> { | |
| 197 | 183 | auto tmp = *this; |
| 198 | 184 | --*this; |
| 199 | 185 | return tmp; |
| 200 | 186 | } |
| 201 | 187 | |
| 202 | 188 | _LIBCPP_HIDE_FROM_ABI |
| 203 | friend constexpr bool operator==(__filter_view_iterator const& __x, __filter_view_iterator const& __y) | |
| 189 | friend constexpr bool operator==(__iterator const& __x, __iterator const& __y) | |
| 204 | 190 | requires equality_comparable<iterator_t<_View>> |
| 205 | 191 | { |
| 206 | 192 | return __x.__current_ == __y.__current_; |
| 207 | 193 | } |
| 208 | 194 | |
| 209 | 195 | _LIBCPP_HIDE_FROM_ABI |
| 210 | friend constexpr range_rvalue_reference_t<_View> iter_move(__filter_view_iterator const& __it) | |
| 196 | friend constexpr range_rvalue_reference_t<_View> iter_move(__iterator const& __it) | |
| 211 | 197 | noexcept(noexcept(ranges::iter_move(__it.__current_))) |
| 212 | 198 | { |
| 213 | 199 | return ranges::iter_move(__it.__current_); |
| 214 | 200 | } |
| 215 | 201 | |
| 216 | 202 | _LIBCPP_HIDE_FROM_ABI |
| 217 | friend constexpr void iter_swap(__filter_view_iterator const& __x, __filter_view_iterator const& __y) | |
| 203 | friend constexpr void iter_swap(__iterator const& __x, __iterator const& __y) | |
| 218 | 204 | noexcept(noexcept(ranges::iter_swap(__x.__current_, __y.__current_))) |
| 219 | 205 | requires indirectly_swappable<iterator_t<_View>> |
| 220 | 206 | { |
| ... | ... | @@ -224,17 +210,15 @@ namespace ranges { |
| 224 | 210 | |
| 225 | 211 | template<input_range _View, indirect_unary_predicate<iterator_t<_View>> _Pred> |
| 226 | 212 | requires view<_View> && is_object_v<_Pred> |
| 227 | class __filter_view_sentinel { | |
| 228 | using __filter_view = filter_view<_View, _Pred>; | |
| 229 | ||
| 213 | class filter_view<_View, _Pred>::__sentinel { | |
| 230 | 214 | public: |
| 231 | 215 | sentinel_t<_View> __end_ = sentinel_t<_View>(); |
| 232 | 216 | |
| 233 | 217 | _LIBCPP_HIDE_FROM_ABI |
| 234 | __filter_view_sentinel() = default; | |
| 218 | __sentinel() = default; | |
| 235 | 219 | |
| 236 | 220 | _LIBCPP_HIDE_FROM_ABI |
| 237 | constexpr explicit __filter_view_sentinel(__filter_view& __parent) | |
| 221 | constexpr explicit __sentinel(filter_view& __parent) | |
| 238 | 222 | : __end_(ranges::end(__parent.__base_)) |
| 239 | 223 | { } |
| 240 | 224 | |
| ... | ... | @@ -242,7 +226,7 @@ namespace ranges { |
| 242 | 226 | constexpr sentinel_t<_View> base() const { return __end_; } |
| 243 | 227 | |
| 244 | 228 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool |
| 245 | operator==(__filter_view_iterator<_View, _Pred> const& __x, __filter_view_sentinel const& __y) { | |
| 229 | operator==(__iterator const& __x, __sentinel const& __y) { | |
| 246 | 230 | return __x.__current_ == __y.__end_; |
| 247 | 231 | } |
| 248 | 232 | }; |
lib/libcxx/include/__ranges/iota_view.h+204-228| ... | ... | @@ -83,14 +83,6 @@ namespace ranges { |
| 83 | 83 | { __j - __j } -> convertible_to<_IotaDiffT<_Iter>>; |
| 84 | 84 | }; |
| 85 | 85 | |
| 86 | template <weakly_incrementable _Start> | |
| 87 | requires copyable<_Start> | |
| 88 | struct __iota_view_iterator; | |
| 89 | ||
| 90 | template <weakly_incrementable _Start, semiregular _BoundSentinel> | |
| 91 | requires __weakly_equality_comparable_with<_Start, _BoundSentinel> && copyable<_Start> | |
| 92 | struct __iota_view_sentinel; | |
| 93 | ||
| 94 | 86 | template<class> |
| 95 | 87 | struct __iota_iterator_category {}; |
| 96 | 88 | |
| ... | ... | @@ -102,9 +94,211 @@ namespace ranges { |
| 102 | 94 | template <weakly_incrementable _Start, semiregular _BoundSentinel = unreachable_sentinel_t> |
| 103 | 95 | requires __weakly_equality_comparable_with<_Start, _BoundSentinel> && copyable<_Start> |
| 104 | 96 | class iota_view : public view_interface<iota_view<_Start, _BoundSentinel>> { |
| 97 | struct __iterator : public __iota_iterator_category<_Start> { | |
| 98 | friend class iota_view; | |
| 99 | ||
| 100 | using iterator_concept = | |
| 101 | _If<__advanceable<_Start>, random_access_iterator_tag, | |
| 102 | _If<__decrementable<_Start>, bidirectional_iterator_tag, | |
| 103 | _If<incrementable<_Start>, forward_iterator_tag, | |
| 104 | /*Else*/ input_iterator_tag>>>; | |
| 105 | ||
| 106 | using value_type = _Start; | |
| 107 | using difference_type = _IotaDiffT<_Start>; | |
| 108 | ||
| 109 | _Start __value_ = _Start(); | |
| 110 | ||
| 111 | _LIBCPP_HIDE_FROM_ABI | |
| 112 | __iterator() requires default_initializable<_Start> = default; | |
| 113 | ||
| 114 | _LIBCPP_HIDE_FROM_ABI | |
| 115 | constexpr explicit __iterator(_Start __value) : __value_(std::move(__value)) {} | |
| 116 | ||
| 117 | _LIBCPP_HIDE_FROM_ABI | |
| 118 | constexpr _Start operator*() const noexcept(is_nothrow_copy_constructible_v<_Start>) { | |
| 119 | return __value_; | |
| 120 | } | |
| 121 | ||
| 122 | _LIBCPP_HIDE_FROM_ABI | |
| 123 | constexpr __iterator& operator++() { | |
| 124 | ++__value_; | |
| 125 | return *this; | |
| 126 | } | |
| 127 | ||
| 128 | _LIBCPP_HIDE_FROM_ABI | |
| 129 | constexpr void operator++(int) { ++*this; } | |
| 130 | ||
| 131 | _LIBCPP_HIDE_FROM_ABI | |
| 132 | constexpr __iterator operator++(int) requires incrementable<_Start> { | |
| 133 | auto __tmp = *this; | |
| 134 | ++*this; | |
| 135 | return __tmp; | |
| 136 | } | |
| 137 | ||
| 138 | _LIBCPP_HIDE_FROM_ABI | |
| 139 | constexpr __iterator& operator--() requires __decrementable<_Start> { | |
| 140 | --__value_; | |
| 141 | return *this; | |
| 142 | } | |
| 143 | ||
| 144 | _LIBCPP_HIDE_FROM_ABI | |
| 145 | constexpr __iterator operator--(int) requires __decrementable<_Start> { | |
| 146 | auto __tmp = *this; | |
| 147 | --*this; | |
| 148 | return __tmp; | |
| 149 | } | |
| 150 | ||
| 151 | _LIBCPP_HIDE_FROM_ABI | |
| 152 | constexpr __iterator& operator+=(difference_type __n) | |
| 153 | requires __advanceable<_Start> | |
| 154 | { | |
| 155 | if constexpr (__integer_like<_Start> && !__signed_integer_like<_Start>) { | |
| 156 | if (__n >= difference_type(0)) { | |
| 157 | __value_ += static_cast<_Start>(__n); | |
| 158 | } else { | |
| 159 | __value_ -= static_cast<_Start>(-__n); | |
| 160 | } | |
| 161 | } else { | |
| 162 | __value_ += __n; | |
| 163 | } | |
| 164 | return *this; | |
| 165 | } | |
| 166 | ||
| 167 | _LIBCPP_HIDE_FROM_ABI | |
| 168 | constexpr __iterator& operator-=(difference_type __n) | |
| 169 | requires __advanceable<_Start> | |
| 170 | { | |
| 171 | if constexpr (__integer_like<_Start> && !__signed_integer_like<_Start>) { | |
| 172 | if (__n >= difference_type(0)) { | |
| 173 | __value_ -= static_cast<_Start>(__n); | |
| 174 | } else { | |
| 175 | __value_ += static_cast<_Start>(-__n); | |
| 176 | } | |
| 177 | } else { | |
| 178 | __value_ -= __n; | |
| 179 | } | |
| 180 | return *this; | |
| 181 | } | |
| 182 | ||
| 183 | _LIBCPP_HIDE_FROM_ABI | |
| 184 | constexpr _Start operator[](difference_type __n) const | |
| 185 | requires __advanceable<_Start> | |
| 186 | { | |
| 187 | return _Start(__value_ + __n); | |
| 188 | } | |
| 189 | ||
| 190 | _LIBCPP_HIDE_FROM_ABI | |
| 191 | friend constexpr bool operator==(const __iterator& __x, const __iterator& __y) | |
| 192 | requires equality_comparable<_Start> | |
| 193 | { | |
| 194 | return __x.__value_ == __y.__value_; | |
| 195 | } | |
| 105 | 196 | |
| 106 | using __iterator = __iota_view_iterator<_Start>; | |
| 107 | using __sentinel = __iota_view_sentinel<_Start, _BoundSentinel>; | |
| 197 | _LIBCPP_HIDE_FROM_ABI | |
| 198 | friend constexpr bool operator<(const __iterator& __x, const __iterator& __y) | |
| 199 | requires totally_ordered<_Start> | |
| 200 | { | |
| 201 | return __x.__value_ < __y.__value_; | |
| 202 | } | |
| 203 | ||
| 204 | _LIBCPP_HIDE_FROM_ABI | |
| 205 | friend constexpr bool operator>(const __iterator& __x, const __iterator& __y) | |
| 206 | requires totally_ordered<_Start> | |
| 207 | { | |
| 208 | return __y < __x; | |
| 209 | } | |
| 210 | ||
| 211 | _LIBCPP_HIDE_FROM_ABI | |
| 212 | friend constexpr bool operator<=(const __iterator& __x, const __iterator& __y) | |
| 213 | requires totally_ordered<_Start> | |
| 214 | { | |
| 215 | return !(__y < __x); | |
| 216 | } | |
| 217 | ||
| 218 | _LIBCPP_HIDE_FROM_ABI | |
| 219 | friend constexpr bool operator>=(const __iterator& __x, const __iterator& __y) | |
| 220 | requires totally_ordered<_Start> | |
| 221 | { | |
| 222 | return !(__x < __y); | |
| 223 | } | |
| 224 | ||
| 225 | _LIBCPP_HIDE_FROM_ABI | |
| 226 | friend constexpr auto operator<=>(const __iterator& __x, const __iterator& __y) | |
| 227 | requires totally_ordered<_Start> && three_way_comparable<_Start> | |
| 228 | { | |
| 229 | return __x.__value_ <=> __y.__value_; | |
| 230 | } | |
| 231 | ||
| 232 | _LIBCPP_HIDE_FROM_ABI | |
| 233 | friend constexpr __iterator operator+(__iterator __i, difference_type __n) | |
| 234 | requires __advanceable<_Start> | |
| 235 | { | |
| 236 | __i += __n; | |
| 237 | return __i; | |
| 238 | } | |
| 239 | ||
| 240 | _LIBCPP_HIDE_FROM_ABI | |
| 241 | friend constexpr __iterator operator+(difference_type __n, __iterator __i) | |
| 242 | requires __advanceable<_Start> | |
| 243 | { | |
| 244 | return __i + __n; | |
| 245 | } | |
| 246 | ||
| 247 | _LIBCPP_HIDE_FROM_ABI | |
| 248 | friend constexpr __iterator operator-(__iterator __i, difference_type __n) | |
| 249 | requires __advanceable<_Start> | |
| 250 | { | |
| 251 | __i -= __n; | |
| 252 | return __i; | |
| 253 | } | |
| 254 | ||
| 255 | _LIBCPP_HIDE_FROM_ABI | |
| 256 | friend constexpr difference_type operator-(const __iterator& __x, const __iterator& __y) | |
| 257 | requires __advanceable<_Start> | |
| 258 | { | |
| 259 | if constexpr (__integer_like<_Start>) { | |
| 260 | if constexpr (__signed_integer_like<_Start>) { | |
| 261 | return difference_type(difference_type(__x.__value_) - difference_type(__y.__value_)); | |
| 262 | } | |
| 263 | if (__y.__value_ > __x.__value_) { | |
| 264 | return difference_type(-difference_type(__y.__value_ - __x.__value_)); | |
| 265 | } | |
| 266 | return difference_type(__x.__value_ - __y.__value_); | |
| 267 | } | |
| 268 | return __x.__value_ - __y.__value_; | |
| 269 | } | |
| 270 | }; | |
| 271 | ||
| 272 | struct __sentinel { | |
| 273 | friend class iota_view; | |
| 274 | ||
| 275 | private: | |
| 276 | _BoundSentinel __bound_sentinel_ = _BoundSentinel(); | |
| 277 | ||
| 278 | public: | |
| 279 | _LIBCPP_HIDE_FROM_ABI | |
| 280 | __sentinel() = default; | |
| 281 | constexpr explicit __sentinel(_BoundSentinel __bound_sentinel) : __bound_sentinel_(std::move(__bound_sentinel)) {} | |
| 282 | ||
| 283 | _LIBCPP_HIDE_FROM_ABI | |
| 284 | friend constexpr bool operator==(const __iterator& __x, const __sentinel& __y) { | |
| 285 | return __x.__value_ == __y.__bound_sentinel_; | |
| 286 | } | |
| 287 | ||
| 288 | _LIBCPP_HIDE_FROM_ABI | |
| 289 | friend constexpr iter_difference_t<_Start> operator-(const __iterator& __x, const __sentinel& __y) | |
| 290 | requires sized_sentinel_for<_BoundSentinel, _Start> | |
| 291 | { | |
| 292 | return __x.__value_ - __y.__bound_sentinel_; | |
| 293 | } | |
| 294 | ||
| 295 | _LIBCPP_HIDE_FROM_ABI | |
| 296 | friend constexpr iter_difference_t<_Start> operator-(const __sentinel& __x, const __iterator& __y) | |
| 297 | requires sized_sentinel_for<_BoundSentinel, _Start> | |
| 298 | { | |
| 299 | return -(__y - __x); | |
| 300 | } | |
| 301 | }; | |
| 108 | 302 | |
| 109 | 303 | _Start __value_ = _Start(); |
| 110 | 304 | _BoundSentinel __bound_sentinel_ = _BoundSentinel(); |
| ... | ... | @@ -185,224 +379,6 @@ namespace ranges { |
| 185 | 379 | template <class _Start, class _BoundSentinel> |
| 186 | 380 | inline constexpr bool enable_borrowed_range<iota_view<_Start, _BoundSentinel>> = true; |
| 187 | 381 | |
| 188 | template <weakly_incrementable _Start> | |
| 189 | requires copyable<_Start> | |
| 190 | struct __iota_view_iterator : public __iota_iterator_category<_Start> { | |
| 191 | ||
| 192 | template <weakly_incrementable _StartT, semiregular _BoundSentinelT> | |
| 193 | requires __weakly_equality_comparable_with<_StartT, _BoundSentinelT> && copyable<_StartT> | |
| 194 | friend class iota_view; | |
| 195 | ||
| 196 | using iterator_concept = | |
| 197 | _If<__advanceable<_Start>, random_access_iterator_tag, | |
| 198 | _If<__decrementable<_Start>, bidirectional_iterator_tag, | |
| 199 | _If<incrementable<_Start>, forward_iterator_tag, | |
| 200 | /*Else*/ input_iterator_tag>>>; | |
| 201 | ||
| 202 | using value_type = _Start; | |
| 203 | using difference_type = _IotaDiffT<_Start>; | |
| 204 | ||
| 205 | _Start __value_ = _Start(); | |
| 206 | ||
| 207 | _LIBCPP_HIDE_FROM_ABI | |
| 208 | __iota_view_iterator() requires default_initializable<_Start> = default; | |
| 209 | ||
| 210 | _LIBCPP_HIDE_FROM_ABI | |
| 211 | constexpr explicit __iota_view_iterator(_Start __value) : __value_(std::move(__value)) {} | |
| 212 | ||
| 213 | _LIBCPP_HIDE_FROM_ABI | |
| 214 | constexpr _Start operator*() const noexcept(is_nothrow_copy_constructible_v<_Start>) { | |
| 215 | return __value_; | |
| 216 | } | |
| 217 | ||
| 218 | _LIBCPP_HIDE_FROM_ABI | |
| 219 | constexpr __iota_view_iterator& operator++() { | |
| 220 | ++__value_; | |
| 221 | return *this; | |
| 222 | } | |
| 223 | ||
| 224 | _LIBCPP_HIDE_FROM_ABI | |
| 225 | constexpr void operator++(int) { ++*this; } | |
| 226 | ||
| 227 | _LIBCPP_HIDE_FROM_ABI | |
| 228 | constexpr __iota_view_iterator operator++(int) requires incrementable<_Start> { | |
| 229 | auto __tmp = *this; | |
| 230 | ++*this; | |
| 231 | return __tmp; | |
| 232 | } | |
| 233 | ||
| 234 | _LIBCPP_HIDE_FROM_ABI | |
| 235 | constexpr __iota_view_iterator& operator--() requires __decrementable<_Start> { | |
| 236 | --__value_; | |
| 237 | return *this; | |
| 238 | } | |
| 239 | ||
| 240 | _LIBCPP_HIDE_FROM_ABI | |
| 241 | constexpr __iota_view_iterator operator--(int) requires __decrementable<_Start> { | |
| 242 | auto __tmp = *this; | |
| 243 | --*this; | |
| 244 | return __tmp; | |
| 245 | } | |
| 246 | ||
| 247 | _LIBCPP_HIDE_FROM_ABI | |
| 248 | constexpr __iota_view_iterator& operator+=(difference_type __n) | |
| 249 | requires __advanceable<_Start> | |
| 250 | { | |
| 251 | if constexpr (__integer_like<_Start> && !__signed_integer_like<_Start>) { | |
| 252 | if (__n >= difference_type(0)) { | |
| 253 | __value_ += static_cast<_Start>(__n); | |
| 254 | } else { | |
| 255 | __value_ -= static_cast<_Start>(-__n); | |
| 256 | } | |
| 257 | } else { | |
| 258 | __value_ += __n; | |
| 259 | } | |
| 260 | return *this; | |
| 261 | } | |
| 262 | ||
| 263 | _LIBCPP_HIDE_FROM_ABI | |
| 264 | constexpr __iota_view_iterator& operator-=(difference_type __n) | |
| 265 | requires __advanceable<_Start> | |
| 266 | { | |
| 267 | if constexpr (__integer_like<_Start> && !__signed_integer_like<_Start>) { | |
| 268 | if (__n >= difference_type(0)) { | |
| 269 | __value_ -= static_cast<_Start>(__n); | |
| 270 | } else { | |
| 271 | __value_ += static_cast<_Start>(-__n); | |
| 272 | } | |
| 273 | } else { | |
| 274 | __value_ -= __n; | |
| 275 | } | |
| 276 | return *this; | |
| 277 | } | |
| 278 | ||
| 279 | _LIBCPP_HIDE_FROM_ABI | |
| 280 | constexpr _Start operator[](difference_type __n) const | |
| 281 | requires __advanceable<_Start> | |
| 282 | { | |
| 283 | return _Start(__value_ + __n); | |
| 284 | } | |
| 285 | ||
| 286 | _LIBCPP_HIDE_FROM_ABI | |
| 287 | friend constexpr bool operator==(const __iota_view_iterator& __x, const __iota_view_iterator& __y) | |
| 288 | requires equality_comparable<_Start> | |
| 289 | { | |
| 290 | return __x.__value_ == __y.__value_; | |
| 291 | } | |
| 292 | ||
| 293 | _LIBCPP_HIDE_FROM_ABI | |
| 294 | friend constexpr bool operator<(const __iota_view_iterator& __x, const __iota_view_iterator& __y) | |
| 295 | requires totally_ordered<_Start> | |
| 296 | { | |
| 297 | return __x.__value_ < __y.__value_; | |
| 298 | } | |
| 299 | ||
| 300 | _LIBCPP_HIDE_FROM_ABI | |
| 301 | friend constexpr bool operator>(const __iota_view_iterator& __x, const __iota_view_iterator& __y) | |
| 302 | requires totally_ordered<_Start> | |
| 303 | { | |
| 304 | return __y < __x; | |
| 305 | } | |
| 306 | ||
| 307 | _LIBCPP_HIDE_FROM_ABI | |
| 308 | friend constexpr bool operator<=(const __iota_view_iterator& __x, const __iota_view_iterator& __y) | |
| 309 | requires totally_ordered<_Start> | |
| 310 | { | |
| 311 | return !(__y < __x); | |
| 312 | } | |
| 313 | ||
| 314 | _LIBCPP_HIDE_FROM_ABI | |
| 315 | friend constexpr bool operator>=(const __iota_view_iterator& __x, const __iota_view_iterator& __y) | |
| 316 | requires totally_ordered<_Start> | |
| 317 | { | |
| 318 | return !(__x < __y); | |
| 319 | } | |
| 320 | ||
| 321 | _LIBCPP_HIDE_FROM_ABI | |
| 322 | friend constexpr auto operator<=>(const __iota_view_iterator& __x, const __iota_view_iterator& __y) | |
| 323 | requires totally_ordered<_Start> && three_way_comparable<_Start> | |
| 324 | { | |
| 325 | return __x.__value_ <=> __y.__value_; | |
| 326 | } | |
| 327 | ||
| 328 | _LIBCPP_HIDE_FROM_ABI | |
| 329 | friend constexpr __iota_view_iterator operator+(__iota_view_iterator __i, difference_type __n) | |
| 330 | requires __advanceable<_Start> | |
| 331 | { | |
| 332 | __i += __n; | |
| 333 | return __i; | |
| 334 | } | |
| 335 | ||
| 336 | _LIBCPP_HIDE_FROM_ABI | |
| 337 | friend constexpr __iota_view_iterator operator+(difference_type __n, __iota_view_iterator __i) | |
| 338 | requires __advanceable<_Start> | |
| 339 | { | |
| 340 | return __i + __n; | |
| 341 | } | |
| 342 | ||
| 343 | _LIBCPP_HIDE_FROM_ABI | |
| 344 | friend constexpr __iota_view_iterator operator-(__iota_view_iterator __i, difference_type __n) | |
| 345 | requires __advanceable<_Start> | |
| 346 | { | |
| 347 | __i -= __n; | |
| 348 | return __i; | |
| 349 | } | |
| 350 | ||
| 351 | _LIBCPP_HIDE_FROM_ABI | |
| 352 | friend constexpr difference_type operator-(const __iota_view_iterator& __x, const __iota_view_iterator& __y) | |
| 353 | requires __advanceable<_Start> | |
| 354 | { | |
| 355 | if constexpr (__integer_like<_Start>) { | |
| 356 | if constexpr (__signed_integer_like<_Start>) { | |
| 357 | return difference_type(difference_type(__x.__value_) - difference_type(__y.__value_)); | |
| 358 | } | |
| 359 | if (__y.__value_ > __x.__value_) { | |
| 360 | return difference_type(-difference_type(__y.__value_ - __x.__value_)); | |
| 361 | } | |
| 362 | return difference_type(__x.__value_ - __y.__value_); | |
| 363 | } | |
| 364 | return __x.__value_ - __y.__value_; | |
| 365 | } | |
| 366 | }; | |
| 367 | ||
| 368 | template <weakly_incrementable _Start, semiregular _BoundSentinel> | |
| 369 | requires __weakly_equality_comparable_with<_Start, _BoundSentinel> && copyable<_Start> | |
| 370 | struct __iota_view_sentinel { | |
| 371 | ||
| 372 | template <weakly_incrementable _StartT, semiregular _BoundSentinelT> | |
| 373 | requires __weakly_equality_comparable_with<_StartT, _BoundSentinelT> && copyable<_StartT> | |
| 374 | friend class iota_view; | |
| 375 | ||
| 376 | using __iterator = __iota_view_iterator<_Start>; | |
| 377 | ||
| 378 | private: | |
| 379 | _BoundSentinel __bound_sentinel_ = _BoundSentinel(); | |
| 380 | ||
| 381 | public: | |
| 382 | _LIBCPP_HIDE_FROM_ABI | |
| 383 | __iota_view_sentinel() = default; | |
| 384 | constexpr explicit __iota_view_sentinel(_BoundSentinel __bound_sentinel) : __bound_sentinel_(std::move(__bound_sentinel)) {} | |
| 385 | ||
| 386 | _LIBCPP_HIDE_FROM_ABI | |
| 387 | friend constexpr bool operator==(const __iterator& __x, const __iota_view_sentinel& __y) { | |
| 388 | return __x.__value_ == __y.__bound_sentinel_; | |
| 389 | } | |
| 390 | ||
| 391 | _LIBCPP_HIDE_FROM_ABI | |
| 392 | friend constexpr iter_difference_t<_Start> operator-(const __iterator& __x, const __iota_view_sentinel& __y) | |
| 393 | requires sized_sentinel_for<_BoundSentinel, _Start> | |
| 394 | { | |
| 395 | return __x.__value_ - __y.__bound_sentinel_; | |
| 396 | } | |
| 397 | ||
| 398 | _LIBCPP_HIDE_FROM_ABI | |
| 399 | friend constexpr iter_difference_t<_Start> operator-(const __iota_view_sentinel& __x, const __iterator& __y) | |
| 400 | requires sized_sentinel_for<_BoundSentinel, _Start> | |
| 401 | { | |
| 402 | return -(__y - __x); | |
| 403 | } | |
| 404 | }; | |
| 405 | ||
| 406 | 382 | namespace views { |
| 407 | 383 | namespace __iota { |
| 408 | 384 | struct __fn { |
lib/libcxx/include/__ranges/istream_view.h+9-17| ... | ... | @@ -36,18 +36,10 @@ namespace ranges { |
| 36 | 36 | template <class _Val, class _CharT, class _Traits> |
| 37 | 37 | concept __stream_extractable = requires(basic_istream<_CharT, _Traits>& __is, _Val& __t) { __is >> __t; }; |
| 38 | 38 | |
| 39 | template <movable _Val, class _CharT, class _Traits> | |
| 40 | requires default_initializable<_Val> && __stream_extractable<_Val, _CharT, _Traits> | |
| 41 | class __basic_istream_view_iterator; | |
| 42 | ||
| 43 | 39 | template <movable _Val, class _CharT, class _Traits = char_traits<_CharT>> |
| 44 | 40 | requires default_initializable<_Val> && __stream_extractable<_Val, _CharT, _Traits> |
| 45 | 41 | class basic_istream_view : public view_interface<basic_istream_view<_Val, _CharT, _Traits>> { |
| 46 | using __iterator = __basic_istream_view_iterator<_Val, _CharT, _Traits>; | |
| 47 | ||
| 48 | template <movable _ValueType, class _CharType, class _TraitsType> | |
| 49 | requires default_initializable<_ValueType> && __stream_extractable<_ValueType, _CharType, _TraitsType> | |
| 50 | friend class __basic_istream_view_iterator; | |
| 42 | class __iterator; | |
| 51 | 43 | |
| 52 | 44 | public: |
| 53 | 45 | _LIBCPP_HIDE_FROM_ABI constexpr explicit basic_istream_view(basic_istream<_CharT, _Traits>& __stream) |
| ... | ... | @@ -67,23 +59,23 @@ private: |
| 67 | 59 | |
| 68 | 60 | template <movable _Val, class _CharT, class _Traits> |
| 69 | 61 | requires default_initializable<_Val> && __stream_extractable<_Val, _CharT, _Traits> |
| 70 | class __basic_istream_view_iterator { | |
| 62 | class basic_istream_view<_Val, _CharT, _Traits>::__iterator { | |
| 71 | 63 | public: |
| 72 | 64 | using iterator_concept = input_iterator_tag; |
| 73 | 65 | using difference_type = ptrdiff_t; |
| 74 | 66 | using value_type = _Val; |
| 75 | 67 | |
| 76 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __basic_istream_view_iterator( | |
| 68 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __iterator( | |
| 77 | 69 | basic_istream_view<_Val, _CharT, _Traits>& __parent) noexcept |
| 78 | 70 | : __parent_(std::addressof(__parent)) {} |
| 79 | 71 | |
| 80 | __basic_istream_view_iterator(const __basic_istream_view_iterator&) = delete; | |
| 81 | _LIBCPP_HIDE_FROM_ABI __basic_istream_view_iterator(__basic_istream_view_iterator&&) = default; | |
| 72 | __iterator(const __iterator&) = delete; | |
| 73 | _LIBCPP_HIDE_FROM_ABI __iterator(__iterator&&) = default; | |
| 82 | 74 | |
| 83 | __basic_istream_view_iterator& operator=(const __basic_istream_view_iterator&) = delete; | |
| 84 | _LIBCPP_HIDE_FROM_ABI __basic_istream_view_iterator& operator=(__basic_istream_view_iterator&&) = default; | |
| 75 | __iterator& operator=(const __iterator&) = delete; | |
| 76 | _LIBCPP_HIDE_FROM_ABI __iterator& operator=(__iterator&&) = default; | |
| 85 | 77 | |
| 86 | _LIBCPP_HIDE_FROM_ABI __basic_istream_view_iterator& operator++() { | |
| 78 | _LIBCPP_HIDE_FROM_ABI __iterator& operator++() { | |
| 87 | 79 | *__parent_->__stream_ >> __parent_->__value_; |
| 88 | 80 | return *this; |
| 89 | 81 | } |
| ... | ... | @@ -92,7 +84,7 @@ public: |
| 92 | 84 | |
| 93 | 85 | _LIBCPP_HIDE_FROM_ABI _Val& operator*() const { return __parent_->__value_; } |
| 94 | 86 | |
| 95 | _LIBCPP_HIDE_FROM_ABI friend bool operator==(const __basic_istream_view_iterator& __x, default_sentinel_t) { | |
| 87 | _LIBCPP_HIDE_FROM_ABI friend bool operator==(const __iterator& __x, default_sentinel_t) { | |
| 96 | 88 | return !*__x.__get_parent_stream(); |
| 97 | 89 | } |
| 98 | 90 |
lib/libcxx/include/__ranges/join_view.h+43-53| ... | ... | @@ -40,7 +40,10 @@ |
| 40 | 40 | |
| 41 | 41 | _LIBCPP_BEGIN_NAMESPACE_STD |
| 42 | 42 | |
| 43 | #if _LIBCPP_STD_VER > 17 | |
| 43 | // Note: `join_view` is still marked experimental because there is an ABI-breaking change that affects `join_view` in | |
| 44 | // the pipeline (https://isocpp.org/files/papers/D2770R0.html). | |
| 45 | // TODO: make `join_view` non-experimental once D2770 is implemented. | |
| 46 | #if _LIBCPP_STD_VER > 17 && defined(_LIBCPP_ENABLE_EXPERIMENTAL) | |
| 44 | 47 | |
| 45 | 48 | namespace ranges { |
| 46 | 49 | template<class> |
| ... | ... | @@ -66,14 +69,6 @@ namespace ranges { |
| 66 | 69 | >; |
| 67 | 70 | }; |
| 68 | 71 | |
| 69 | template <input_range _View, bool _Const> | |
| 70 | requires view<_View> && input_range<range_reference_t<_View>> | |
| 71 | struct __join_view_iterator; | |
| 72 | ||
| 73 | template <input_range _View, bool _Const> | |
| 74 | requires view<_View> && input_range<range_reference_t<_View>> | |
| 75 | struct __join_view_sentinel; | |
| 76 | ||
| 77 | 72 | template<input_range _View> |
| 78 | 73 | requires view<_View> && input_range<range_reference_t<_View>> |
| 79 | 74 | class join_view |
| ... | ... | @@ -81,19 +76,9 @@ namespace ranges { |
| 81 | 76 | private: |
| 82 | 77 | using _InnerRange = range_reference_t<_View>; |
| 83 | 78 | |
| 84 | template<bool _Const> | |
| 85 | using __iterator = __join_view_iterator<_View, _Const>; | |
| 86 | ||
| 87 | template<bool _Const> | |
| 88 | using __sentinel = __join_view_sentinel<_View, _Const>; | |
| 79 | template<bool> struct __iterator; | |
| 89 | 80 | |
| 90 | template <input_range _View2, bool _Const2> | |
| 91 | requires view<_View2> && input_range<range_reference_t<_View2>> | |
| 92 | friend struct __join_view_iterator; | |
| 93 | ||
| 94 | template <input_range _View2, bool _Const2> | |
| 95 | requires view<_View2> && input_range<range_reference_t<_View2>> | |
| 96 | friend struct __join_view_sentinel; | |
| 81 | template<bool> struct __sentinel; | |
| 97 | 82 | |
| 98 | 83 | template <class> |
| 99 | 84 | friend struct std::__segmented_iterator_traits; |
| ... | ... | @@ -164,12 +149,12 @@ namespace ranges { |
| 164 | 149 | } |
| 165 | 150 | }; |
| 166 | 151 | |
| 167 | template<input_range _View, bool _Const> | |
| 152 | template<input_range _View> | |
| 168 | 153 | requires view<_View> && input_range<range_reference_t<_View>> |
| 169 | struct __join_view_sentinel { | |
| 170 | template<input_range _View2, bool> | |
| 171 | requires view<_View2> && input_range<range_reference_t<_View2>> | |
| 172 | friend struct __join_view_sentinel; | |
| 154 | template<bool _Const> | |
| 155 | struct join_view<_View>::__sentinel { | |
| 156 | template<bool> | |
| 157 | friend struct __sentinel; | |
| 173 | 158 | |
| 174 | 159 | private: |
| 175 | 160 | using _Parent = __maybe_const<_Const, join_view<_View>>; |
| ... | ... | @@ -178,37 +163,42 @@ namespace ranges { |
| 178 | 163 | |
| 179 | 164 | public: |
| 180 | 165 | _LIBCPP_HIDE_FROM_ABI |
| 181 | __join_view_sentinel() = default; | |
| 166 | __sentinel() = default; | |
| 182 | 167 | |
| 183 | 168 | _LIBCPP_HIDE_FROM_ABI |
| 184 | constexpr explicit __join_view_sentinel(_Parent& __parent) | |
| 169 | constexpr explicit __sentinel(_Parent& __parent) | |
| 185 | 170 | : __end_(ranges::end(__parent.__base_)) {} |
| 186 | 171 | |
| 187 | 172 | _LIBCPP_HIDE_FROM_ABI |
| 188 | constexpr __join_view_sentinel(__join_view_sentinel<_View, !_Const> __s) | |
| 173 | constexpr __sentinel(__sentinel<!_Const> __s) | |
| 189 | 174 | requires _Const && convertible_to<sentinel_t<_View>, sentinel_t<_Base>> |
| 190 | 175 | : __end_(std::move(__s.__end_)) {} |
| 191 | 176 | |
| 192 | 177 | template<bool _OtherConst> |
| 193 | 178 | requires sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 194 | 179 | _LIBCPP_HIDE_FROM_ABI |
| 195 | friend constexpr bool operator==(const __join_view_iterator<_View, _OtherConst>& __x, const __join_view_sentinel& __y) { | |
| 180 | friend constexpr bool operator==(const __iterator<_OtherConst>& __x, const __sentinel& __y) { | |
| 196 | 181 | return __x.__outer_ == __y.__end_; |
| 197 | 182 | } |
| 198 | 183 | }; |
| 199 | 184 | |
| 200 | template<input_range _View, bool _Const> | |
| 185 | // https://reviews.llvm.org/D142811#inline-1383022 | |
| 186 | // To simplify the segmented iterator traits specialization, | |
| 187 | // make the iterator `final` | |
| 188 | template<input_range _View> | |
| 201 | 189 | requires view<_View> && input_range<range_reference_t<_View>> |
| 202 | struct __join_view_iterator | |
| 190 | template<bool _Const> | |
| 191 | struct join_view<_View>::__iterator final | |
| 203 | 192 | : public __join_view_iterator_category<__maybe_const<_Const, _View>> { |
| 204 | 193 | |
| 205 | template<input_range _View2, bool> | |
| 206 | requires view<_View2> && input_range<range_reference_t<_View2>> | |
| 207 | friend struct __join_view_iterator; | |
| 194 | template<bool> | |
| 195 | friend struct __iterator; | |
| 208 | 196 | |
| 209 | 197 | template <class> |
| 210 | 198 | friend struct std::__segmented_iterator_traits; |
| 211 | 199 | |
| 200 | static constexpr bool __is_join_view_iterator = true; | |
| 201 | ||
| 212 | 202 | private: |
| 213 | 203 | using _Parent = __maybe_const<_Const, join_view<_View>>; |
| 214 | 204 | using _Base = __maybe_const<_Const, _View>; |
| ... | ... | @@ -243,7 +233,7 @@ namespace ranges { |
| 243 | 233 | __inner_.reset(); |
| 244 | 234 | } |
| 245 | 235 | |
| 246 | _LIBCPP_HIDE_FROM_ABI constexpr __join_view_iterator(_Parent* __parent, _Outer __outer, _Inner __inner) | |
| 236 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator(_Parent* __parent, _Outer __outer, _Inner __inner) | |
| 247 | 237 | : __outer_(std::move(__outer)), __inner_(std::move(__inner)), __parent_(__parent) {} |
| 248 | 238 | |
| 249 | 239 | public: |
| ... | ... | @@ -264,17 +254,17 @@ namespace ranges { |
| 264 | 254 | range_difference_t<_Base>, range_difference_t<range_reference_t<_Base>>>; |
| 265 | 255 | |
| 266 | 256 | _LIBCPP_HIDE_FROM_ABI |
| 267 | __join_view_iterator() requires default_initializable<_Outer> = default; | |
| 257 | __iterator() requires default_initializable<_Outer> = default; | |
| 268 | 258 | |
| 269 | 259 | _LIBCPP_HIDE_FROM_ABI |
| 270 | constexpr __join_view_iterator(_Parent& __parent, _Outer __outer) | |
| 260 | constexpr __iterator(_Parent& __parent, _Outer __outer) | |
| 271 | 261 | : __outer_(std::move(__outer)) |
| 272 | 262 | , __parent_(std::addressof(__parent)) { |
| 273 | 263 | __satisfy(); |
| 274 | 264 | } |
| 275 | 265 | |
| 276 | 266 | _LIBCPP_HIDE_FROM_ABI |
| 277 | constexpr __join_view_iterator(__join_view_iterator<_View, !_Const> __i) | |
| 267 | constexpr __iterator(__iterator<!_Const> __i) | |
| 278 | 268 | requires _Const && |
| 279 | 269 | convertible_to<iterator_t<_View>, _Outer> && |
| 280 | 270 | convertible_to<iterator_t<_InnerRange>, _Inner> |
| ... | ... | @@ -295,7 +285,7 @@ namespace ranges { |
| 295 | 285 | } |
| 296 | 286 | |
| 297 | 287 | _LIBCPP_HIDE_FROM_ABI |
| 298 | constexpr __join_view_iterator& operator++() { | |
| 288 | constexpr __iterator& operator++() { | |
| 299 | 289 | auto&& __inner = [&]() -> auto&& { |
| 300 | 290 | if constexpr (__ref_is_glvalue) |
| 301 | 291 | return *__outer_; |
| ... | ... | @@ -315,7 +305,7 @@ namespace ranges { |
| 315 | 305 | } |
| 316 | 306 | |
| 317 | 307 | _LIBCPP_HIDE_FROM_ABI |
| 318 | constexpr __join_view_iterator operator++(int) | |
| 308 | constexpr __iterator operator++(int) | |
| 319 | 309 | requires __ref_is_glvalue && |
| 320 | 310 | forward_range<_Base> && |
| 321 | 311 | forward_range<range_reference_t<_Base>> |
| ... | ... | @@ -326,7 +316,7 @@ namespace ranges { |
| 326 | 316 | } |
| 327 | 317 | |
| 328 | 318 | _LIBCPP_HIDE_FROM_ABI |
| 329 | constexpr __join_view_iterator& operator--() | |
| 319 | constexpr __iterator& operator--() | |
| 330 | 320 | requires __ref_is_glvalue && |
| 331 | 321 | bidirectional_range<_Base> && |
| 332 | 322 | bidirectional_range<range_reference_t<_Base>> && |
| ... | ... | @@ -345,7 +335,7 @@ namespace ranges { |
| 345 | 335 | } |
| 346 | 336 | |
| 347 | 337 | _LIBCPP_HIDE_FROM_ABI |
| 348 | constexpr __join_view_iterator operator--(int) | |
| 338 | constexpr __iterator operator--(int) | |
| 349 | 339 | requires __ref_is_glvalue && |
| 350 | 340 | bidirectional_range<_Base> && |
| 351 | 341 | bidirectional_range<range_reference_t<_Base>> && |
| ... | ... | @@ -357,7 +347,7 @@ namespace ranges { |
| 357 | 347 | } |
| 358 | 348 | |
| 359 | 349 | _LIBCPP_HIDE_FROM_ABI |
| 360 | friend constexpr bool operator==(const __join_view_iterator& __x, const __join_view_iterator& __y) | |
| 350 | friend constexpr bool operator==(const __iterator& __x, const __iterator& __y) | |
| 361 | 351 | requires __ref_is_glvalue && |
| 362 | 352 | equality_comparable<iterator_t<_Base>> && |
| 363 | 353 | equality_comparable<iterator_t<range_reference_t<_Base>>> |
| ... | ... | @@ -366,14 +356,14 @@ namespace ranges { |
| 366 | 356 | } |
| 367 | 357 | |
| 368 | 358 | _LIBCPP_HIDE_FROM_ABI |
| 369 | friend constexpr decltype(auto) iter_move(const __join_view_iterator& __i) | |
| 359 | friend constexpr decltype(auto) iter_move(const __iterator& __i) | |
| 370 | 360 | noexcept(noexcept(ranges::iter_move(*__i.__inner_))) |
| 371 | 361 | { |
| 372 | 362 | return ranges::iter_move(*__i.__inner_); |
| 373 | 363 | } |
| 374 | 364 | |
| 375 | 365 | _LIBCPP_HIDE_FROM_ABI |
| 376 | friend constexpr void iter_swap(const __join_view_iterator& __x, const __join_view_iterator& __y) | |
| 366 | friend constexpr void iter_swap(const __iterator& __x, const __iterator& __y) | |
| 377 | 367 | noexcept(noexcept(ranges::iter_swap(*__x.__inner_, *__y.__inner_))) |
| 378 | 368 | requires indirectly_swappable<_Inner> |
| 379 | 369 | { |
| ... | ... | @@ -401,12 +391,12 @@ inline namespace __cpo { |
| 401 | 391 | } // namespace views |
| 402 | 392 | } // namespace ranges |
| 403 | 393 | |
| 404 | template <class _View, bool _Const> | |
| 405 | requires(ranges::common_range<typename ranges::__join_view_iterator<_View, _Const>::_Parent> && | |
| 406 | __is_cpp17_random_access_iterator<typename ranges::__join_view_iterator<_View, _Const>::_Outer>::value && | |
| 407 | __is_cpp17_random_access_iterator<typename ranges::__join_view_iterator<_View, _Const>::_Inner>::value) | |
| 408 | struct __segmented_iterator_traits<ranges::__join_view_iterator<_View, _Const>> { | |
| 409 | using _JoinViewIterator = ranges::__join_view_iterator<_View, _Const>; | |
| 394 | template <class _JoinViewIterator> | |
| 395 | requires(_JoinViewIterator::__is_join_view_iterator && | |
| 396 | ranges::common_range<typename _JoinViewIterator::_Parent> && | |
| 397 | __is_cpp17_random_access_iterator<typename _JoinViewIterator::_Outer>::value && | |
| 398 | __is_cpp17_random_access_iterator<typename _JoinViewIterator::_Inner>::value) | |
| 399 | struct __segmented_iterator_traits<_JoinViewIterator> { | |
| 410 | 400 | |
| 411 | 401 | using __segment_iterator = |
| 412 | 402 | _LIBCPP_NODEBUG __iterator_with_data<typename _JoinViewIterator::_Outer, typename _JoinViewIterator::_Parent*>; |
| ... | ... | @@ -445,7 +435,7 @@ struct __segmented_iterator_traits<ranges::__join_view_iterator<_View, _Const>> |
| 445 | 435 | } |
| 446 | 436 | }; |
| 447 | 437 | |
| 448 | #endif // _LIBCPP_STD_VER > 17 | |
| 438 | #endif // #if _LIBCPP_STD_VER > 17 && defined(_LIBCPP_ENABLE_EXPERIMENTAL) | |
| 449 | 439 | |
| 450 | 440 | _LIBCPP_END_NAMESPACE_STD |
| 451 | 441 |
lib/libcxx/include/__ranges/split_view.h+23-29| ... | ... | @@ -42,12 +42,6 @@ _LIBCPP_BEGIN_NAMESPACE_STD |
| 42 | 42 | |
| 43 | 43 | namespace ranges { |
| 44 | 44 | |
| 45 | template <class _View, class _Pattern> | |
| 46 | struct __split_view_iterator; | |
| 47 | ||
| 48 | template <class _View, class _Pattern> | |
| 49 | struct __split_view_sentinel; | |
| 50 | ||
| 51 | 45 | template <forward_range _View, forward_range _Pattern> |
| 52 | 46 | requires view<_View> && view<_Pattern> && |
| 53 | 47 | indirectly_comparable<iterator_t<_View>, iterator_t<_Pattern>, ranges::equal_to> |
| ... | ... | @@ -59,13 +53,13 @@ private: |
| 59 | 53 | _Cache __cached_begin_ = _Cache(); |
| 60 | 54 | |
| 61 | 55 | template <class, class> |
| 62 | friend struct __split_view_iterator; | |
| 56 | friend struct __iterator; | |
| 63 | 57 | |
| 64 | 58 | template <class, class> |
| 65 | friend struct __split_view_sentinel; | |
| 59 | friend struct __sentinel; | |
| 66 | 60 | |
| 67 | using __iterator = __split_view_iterator<_View, _Pattern>; | |
| 68 | using __sentinel = __split_view_sentinel<_View, _Pattern>; | |
| 61 | struct __iterator; | |
| 62 | struct __sentinel; | |
| 69 | 63 | |
| 70 | 64 | _LIBCPP_HIDE_FROM_ABI constexpr subrange<iterator_t<_View>> __find_next(iterator_t<_View> __it) { |
| 71 | 65 | auto [__begin, __end] = ranges::search(subrange(__it, ranges::end(__base_)), __pattern_); |
| ... | ... | @@ -120,16 +114,17 @@ split_view(_Range&&, _Pattern&&) -> split_view<views::all_t<_Range>, views::all_ |
| 120 | 114 | template <forward_range _Range> |
| 121 | 115 | split_view(_Range&&, range_value_t<_Range>) -> split_view<views::all_t<_Range>, single_view<range_value_t<_Range>>>; |
| 122 | 116 | |
| 123 | template <class _View, class _Pattern> | |
| 124 | struct __split_view_iterator { | |
| 117 | template <forward_range _View, forward_range _Pattern> | |
| 118 | requires view<_View> && view<_Pattern> && | |
| 119 | indirectly_comparable<iterator_t<_View>, iterator_t<_Pattern>, ranges::equal_to> | |
| 120 | struct split_view<_View, _Pattern>::__iterator { | |
| 125 | 121 | private: |
| 126 | split_view<_View, _Pattern>* __parent_ = nullptr; | |
| 122 | split_view* __parent_ = nullptr; | |
| 127 | 123 | _LIBCPP_NO_UNIQUE_ADDRESS iterator_t<_View> __cur_ = iterator_t<_View>(); |
| 128 | 124 | _LIBCPP_NO_UNIQUE_ADDRESS subrange<iterator_t<_View>> __next_ = subrange<iterator_t<_View>>(); |
| 129 | 125 | bool __trailing_empty_ = false; |
| 130 | 126 | |
| 131 | template <class, class> | |
| 132 | friend struct __split_view_sentinel; | |
| 127 | friend struct __sentinel; | |
| 133 | 128 | |
| 134 | 129 | public: |
| 135 | 130 | using iterator_concept = forward_iterator_tag; |
| ... | ... | @@ -137,9 +132,9 @@ public: |
| 137 | 132 | using value_type = subrange<iterator_t<_View>>; |
| 138 | 133 | using difference_type = range_difference_t<_View>; |
| 139 | 134 | |
| 140 | _LIBCPP_HIDE_FROM_ABI __split_view_iterator() = default; | |
| 135 | _LIBCPP_HIDE_FROM_ABI __iterator() = default; | |
| 141 | 136 | |
| 142 | _LIBCPP_HIDE_FROM_ABI constexpr __split_view_iterator( | |
| 137 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator( | |
| 143 | 138 | split_view<_View, _Pattern>& __parent, iterator_t<_View> __current, subrange<iterator_t<_View>> __next) |
| 144 | 139 | : __parent_(std::addressof(__parent)), __cur_(std::move(__current)), __next_(std::move(__next)) {} |
| 145 | 140 | |
| ... | ... | @@ -147,7 +142,7 @@ public: |
| 147 | 142 | |
| 148 | 143 | _LIBCPP_HIDE_FROM_ABI constexpr value_type operator*() const { return {__cur_, __next_.begin()}; } |
| 149 | 144 | |
| 150 | _LIBCPP_HIDE_FROM_ABI constexpr __split_view_iterator& operator++() { | |
| 145 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator& operator++() { | |
| 151 | 146 | __cur_ = __next_.begin(); |
| 152 | 147 | if (__cur_ != ranges::end(__parent_->__base_)) { |
| 153 | 148 | __cur_ = __next_.end(); |
| ... | ... | @@ -163,36 +158,35 @@ public: |
| 163 | 158 | return *this; |
| 164 | 159 | } |
| 165 | 160 | |
| 166 | _LIBCPP_HIDE_FROM_ABI constexpr __split_view_iterator operator++(int) { | |
| 161 | _LIBCPP_HIDE_FROM_ABI constexpr __iterator operator++(int) { | |
| 167 | 162 | auto __tmp = *this; |
| 168 | 163 | ++*this; |
| 169 | 164 | return __tmp; |
| 170 | 165 | } |
| 171 | 166 | |
| 172 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 173 | operator==(const __split_view_iterator& __x, const __split_view_iterator& __y) { | |
| 167 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator==(const __iterator& __x, const __iterator& __y) { | |
| 174 | 168 | return __x.__cur_ == __y.__cur_ && __x.__trailing_empty_ == __y.__trailing_empty_; |
| 175 | 169 | } |
| 176 | 170 | }; |
| 177 | 171 | |
| 178 | template <class _View, class _Pattern> | |
| 179 | struct __split_view_sentinel { | |
| 172 | template <forward_range _View, forward_range _Pattern> | |
| 173 | requires view<_View> && view<_Pattern> && | |
| 174 | indirectly_comparable<iterator_t<_View>, iterator_t<_Pattern>, ranges::equal_to> | |
| 175 | struct split_view<_View, _Pattern>::__sentinel { | |
| 180 | 176 | private: |
| 181 | 177 | _LIBCPP_NO_UNIQUE_ADDRESS sentinel_t<_View> __end_ = sentinel_t<_View>(); |
| 182 | 178 | |
| 183 | _LIBCPP_HIDE_FROM_ABI static constexpr bool | |
| 184 | __equals(const __split_view_iterator<_View, _Pattern>& __x, const __split_view_sentinel& __y) { | |
| 179 | _LIBCPP_HIDE_FROM_ABI static constexpr bool __equals(const __iterator& __x, const __sentinel& __y) { | |
| 185 | 180 | return __x.__cur_ == __y.__end_ && !__x.__trailing_empty_; |
| 186 | 181 | } |
| 187 | 182 | |
| 188 | 183 | public: |
| 189 | _LIBCPP_HIDE_FROM_ABI __split_view_sentinel() = default; | |
| 184 | _LIBCPP_HIDE_FROM_ABI __sentinel() = default; | |
| 190 | 185 | |
| 191 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __split_view_sentinel(split_view<_View, _Pattern>& __parent) | |
| 186 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __sentinel(split_view<_View, _Pattern>& __parent) | |
| 192 | 187 | : __end_(ranges::end(__parent.__base_)) {} |
| 193 | 188 | |
| 194 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 195 | operator==(const __split_view_iterator<_View, _Pattern>& __x, const __split_view_sentinel& __y) { | |
| 189 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator==(const __iterator& __x, const __sentinel& __y) { | |
| 196 | 190 | return __equals(__x, __y); |
| 197 | 191 | } |
| 198 | 192 | }; |
lib/libcxx/include/__ranges/take_while_view.h+12-18| ... | ... | @@ -53,17 +53,11 @@ template <class _View, class _Pred> |
| 53 | 53 | concept __take_while_const_is_range = |
| 54 | 54 | range<const _View> && indirect_unary_predicate<const _Pred, iterator_t<const _View>>; |
| 55 | 55 | |
| 56 | template <class, class, bool> | |
| 57 | class __take_while_view_sentinel; | |
| 58 | ||
| 59 | 56 | template <view _View, class _Pred> |
| 60 | 57 | requires input_range<_View> && is_object_v<_Pred> && indirect_unary_predicate<const _Pred, iterator_t<_View>> |
| 61 | 58 | class take_while_view : public view_interface<take_while_view<_View, _Pred>> { |
| 62 | template <class, class, bool> | |
| 63 | friend class __take_while_view_sentinel; | |
| 64 | ||
| 65 | template <bool _Const> | |
| 66 | using __sentinel = __take_while_view_sentinel<_View, _Pred, _Const>; | |
| 59 | template <bool> | |
| 60 | class __sentinel; | |
| 67 | 61 | |
| 68 | 62 | _LIBCPP_NO_UNIQUE_ADDRESS _View __base_ = _View(); |
| 69 | 63 | _LIBCPP_NO_UNIQUE_ADDRESS __copyable_box<_Pred> __pred_; |
| ... | ... | @@ -114,37 +108,37 @@ public: |
| 114 | 108 | template <class _Range, class _Pred> |
| 115 | 109 | take_while_view(_Range&&, _Pred) -> take_while_view<views::all_t<_Range>, _Pred>; |
| 116 | 110 | |
| 117 | template <class _View, class _Pred, bool _Const> | |
| 118 | class __take_while_view_sentinel { | |
| 111 | template <view _View, class _Pred> | |
| 112 | requires input_range<_View> && is_object_v<_Pred> && indirect_unary_predicate<const _Pred, iterator_t<_View>> | |
| 113 | template <bool _Const> | |
| 114 | class take_while_view<_View, _Pred>::__sentinel { | |
| 119 | 115 | using _Base = __maybe_const<_Const, _View>; |
| 120 | 116 | |
| 121 | 117 | sentinel_t<_Base> __end_ = sentinel_t<_Base>(); |
| 122 | 118 | const _Pred* __pred_ = nullptr; |
| 123 | 119 | |
| 124 | template <class, class, bool> | |
| 125 | friend class __take_while_view_sentinel; | |
| 120 | friend class __sentinel<!_Const>; | |
| 126 | 121 | |
| 127 | 122 | public: |
| 128 | _LIBCPP_HIDE_FROM_ABI __take_while_view_sentinel() = default; | |
| 123 | _LIBCPP_HIDE_FROM_ABI __sentinel() = default; | |
| 129 | 124 | |
| 130 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __take_while_view_sentinel(sentinel_t<_Base> __end, const _Pred* __pred) | |
| 125 | _LIBCPP_HIDE_FROM_ABI constexpr explicit __sentinel(sentinel_t<_Base> __end, const _Pred* __pred) | |
| 131 | 126 | : __end_(std::move(__end)), __pred_(__pred) {} |
| 132 | 127 | |
| 133 | _LIBCPP_HIDE_FROM_ABI constexpr __take_while_view_sentinel(__take_while_view_sentinel<_View, _Pred, !_Const> __s) | |
| 128 | _LIBCPP_HIDE_FROM_ABI constexpr __sentinel(__sentinel<!_Const> __s) | |
| 134 | 129 | requires _Const && convertible_to<sentinel_t<_View>, sentinel_t<_Base>> |
| 135 | 130 | : __end_(std::move(__s.__end_)), __pred_(__s.__pred_) {} |
| 136 | 131 | |
| 137 | 132 | _LIBCPP_HIDE_FROM_ABI constexpr sentinel_t<_Base> base() const { return __end_; } |
| 138 | 133 | |
| 139 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool | |
| 140 | operator==(const iterator_t<_Base>& __x, const __take_while_view_sentinel& __y) { | |
| 134 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool operator==(const iterator_t<_Base>& __x, const __sentinel& __y) { | |
| 141 | 135 | return __x == __y.__end_ || !std::invoke(*__y.__pred_, *__x); |
| 142 | 136 | } |
| 143 | 137 | |
| 144 | 138 | template <bool _OtherConst = !_Const> |
| 145 | 139 | requires sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 146 | 140 | _LIBCPP_HIDE_FROM_ABI friend constexpr bool |
| 147 | operator==(const iterator_t<__maybe_const<_OtherConst, _View>>& __x, const __take_while_view_sentinel& __y) { | |
| 141 | operator==(const iterator_t<__maybe_const<_OtherConst, _View>>& __x, const __sentinel& __y) { | |
| 148 | 142 | return __x == __y.__end_ || !std::invoke(*__y.__pred_, *__x); |
| 149 | 143 | } |
| 150 | 144 | }; |
lib/libcxx/include/__ranges/transform_view.h+51-76| ... | ... | @@ -57,31 +57,11 @@ concept __transform_view_constraints = |
| 57 | 57 | regular_invocable<_Fn&, range_reference_t<_View>> && |
| 58 | 58 | __can_reference<invoke_result_t<_Fn&, range_reference_t<_View>>>; |
| 59 | 59 | |
| 60 | template <input_range _View, copy_constructible _Function, bool _IsConst> | |
| 61 | requires __transform_view_constraints<_View, _Function> | |
| 62 | class __transform_view_iterator; | |
| 63 | ||
| 64 | template <input_range _View, copy_constructible _Function, bool _IsConst> | |
| 65 | requires __transform_view_constraints<_View, _Function> | |
| 66 | class __transform_view_sentinel; | |
| 67 | ||
| 68 | 60 | template<input_range _View, copy_constructible _Fn> |
| 69 | 61 | requires __transform_view_constraints<_View, _Fn> |
| 70 | 62 | class transform_view : public view_interface<transform_view<_View, _Fn>> { |
| 71 | ||
| 72 | template <bool _IsConst> | |
| 73 | using __iterator = __transform_view_iterator<_View, _Fn, _IsConst>; | |
| 74 | ||
| 75 | template <bool _IsConst> | |
| 76 | using __sentinel = __transform_view_sentinel<_View, _Fn, _IsConst>; | |
| 77 | ||
| 78 | template <input_range _ViewType, copy_constructible _FunctionType, bool _IsConst> | |
| 79 | requires __transform_view_constraints<_ViewType, _FunctionType> | |
| 80 | friend class __transform_view_iterator; | |
| 81 | ||
| 82 | template <input_range _ViewType, copy_constructible _FunctionType, bool _IsConst> | |
| 83 | requires __transform_view_constraints<_ViewType, _FunctionType> | |
| 84 | friend class __transform_view_sentinel; | |
| 63 | template<bool> class __iterator; | |
| 64 | template<bool> class __sentinel; | |
| 85 | 65 | |
| 86 | 66 | _LIBCPP_NO_UNIQUE_ADDRESS __copyable_box<_Fn> __func_; |
| 87 | 67 | _LIBCPP_NO_UNIQUE_ADDRESS _View __base_ = _View(); |
| ... | ... | @@ -176,23 +156,22 @@ struct __transform_view_iterator_category_base<_View, _Fn> { |
| 176 | 156 | >; |
| 177 | 157 | }; |
| 178 | 158 | |
| 179 | template<input_range _View, copy_constructible _Fn, bool _Const> | |
| 159 | template<input_range _View, copy_constructible _Fn> | |
| 180 | 160 | requires __transform_view_constraints<_View, _Fn> |
| 181 | class __transform_view_iterator | |
| 161 | template<bool _Const> | |
| 162 | class transform_view<_View, _Fn>::__iterator | |
| 182 | 163 | : public __transform_view_iterator_category_base<_View, _Fn> { |
| 183 | 164 | |
| 184 | using _Parent = __maybe_const<_Const, transform_view<_View, _Fn>>; | |
| 165 | using _Parent = __maybe_const<_Const, transform_view>; | |
| 185 | 166 | using _Base = __maybe_const<_Const, _View>; |
| 186 | 167 | |
| 187 | 168 | _Parent *__parent_ = nullptr; |
| 188 | 169 | |
| 189 | template<input_range _ViewType, copy_constructible _FunctionType, bool _IsConst> | |
| 190 | requires __transform_view_constraints<_ViewType, _FunctionType> | |
| 191 | friend class __transform_view_iterator; | |
| 170 | template<bool> | |
| 171 | friend class transform_view<_View, _Fn>::__iterator; | |
| 192 | 172 | |
| 193 | template<input_range _ViewType, copy_constructible _FunctionType, bool _IsConst> | |
| 194 | requires __transform_view_constraints<_ViewType, _FunctionType> | |
| 195 | friend class __transform_view_sentinel; | |
| 173 | template<bool> | |
| 174 | friend class transform_view<_View, _Fn>::__sentinel; | |
| 196 | 175 | |
| 197 | 176 | public: |
| 198 | 177 | iterator_t<_Base> __current_ = iterator_t<_Base>(); |
| ... | ... | @@ -202,17 +181,17 @@ public: |
| 202 | 181 | using difference_type = range_difference_t<_Base>; |
| 203 | 182 | |
| 204 | 183 | _LIBCPP_HIDE_FROM_ABI |
| 205 | __transform_view_iterator() requires default_initializable<iterator_t<_Base>> = default; | |
| 184 | __iterator() requires default_initializable<iterator_t<_Base>> = default; | |
| 206 | 185 | |
| 207 | 186 | _LIBCPP_HIDE_FROM_ABI |
| 208 | constexpr __transform_view_iterator(_Parent& __parent, iterator_t<_Base> __current) | |
| 187 | constexpr __iterator(_Parent& __parent, iterator_t<_Base> __current) | |
| 209 | 188 | : __parent_(std::addressof(__parent)), __current_(std::move(__current)) {} |
| 210 | 189 | |
| 211 | // Note: `__i` should always be `__transform_view_iterator<false>`, but directly using | |
| 212 | // `__transform_view_iterator<false>` is ill-formed when `_Const` is false | |
| 190 | // Note: `__i` should always be `__iterator<false>`, but directly using | |
| 191 | // `__iterator<false>` is ill-formed when `_Const` is false | |
| 213 | 192 | // (see http://wg21.link/class.copy.ctor#5). |
| 214 | 193 | _LIBCPP_HIDE_FROM_ABI |
| 215 | constexpr __transform_view_iterator(__transform_view_iterator<_View, _Fn, !_Const> __i) | |
| 194 | constexpr __iterator(__iterator<!_Const> __i) | |
| 216 | 195 | requires _Const && convertible_to<iterator_t<_View>, iterator_t<_Base>> |
| 217 | 196 | : __parent_(__i.__parent_), __current_(std::move(__i.__current_)) {} |
| 218 | 197 | |
| ... | ... | @@ -234,7 +213,7 @@ public: |
| 234 | 213 | } |
| 235 | 214 | |
| 236 | 215 | _LIBCPP_HIDE_FROM_ABI |
| 237 | constexpr __transform_view_iterator& operator++() { | |
| 216 | constexpr __iterator& operator++() { | |
| 238 | 217 | ++__current_; |
| 239 | 218 | return *this; |
| 240 | 219 | } |
| ... | ... | @@ -243,7 +222,7 @@ public: |
| 243 | 222 | constexpr void operator++(int) { ++__current_; } |
| 244 | 223 | |
| 245 | 224 | _LIBCPP_HIDE_FROM_ABI |
| 246 | constexpr __transform_view_iterator operator++(int) | |
| 225 | constexpr __iterator operator++(int) | |
| 247 | 226 | requires forward_range<_Base> |
| 248 | 227 | { |
| 249 | 228 | auto __tmp = *this; |
| ... | ... | @@ -252,7 +231,7 @@ public: |
| 252 | 231 | } |
| 253 | 232 | |
| 254 | 233 | _LIBCPP_HIDE_FROM_ABI |
| 255 | constexpr __transform_view_iterator& operator--() | |
| 234 | constexpr __iterator& operator--() | |
| 256 | 235 | requires bidirectional_range<_Base> |
| 257 | 236 | { |
| 258 | 237 | --__current_; |
| ... | ... | @@ -260,7 +239,7 @@ public: |
| 260 | 239 | } |
| 261 | 240 | |
| 262 | 241 | _LIBCPP_HIDE_FROM_ABI |
| 263 | constexpr __transform_view_iterator operator--(int) | |
| 242 | constexpr __iterator operator--(int) | |
| 264 | 243 | requires bidirectional_range<_Base> |
| 265 | 244 | { |
| 266 | 245 | auto __tmp = *this; |
| ... | ... | @@ -269,7 +248,7 @@ public: |
| 269 | 248 | } |
| 270 | 249 | |
| 271 | 250 | _LIBCPP_HIDE_FROM_ABI |
| 272 | constexpr __transform_view_iterator& operator+=(difference_type __n) | |
| 251 | constexpr __iterator& operator+=(difference_type __n) | |
| 273 | 252 | requires random_access_range<_Base> |
| 274 | 253 | { |
| 275 | 254 | __current_ += __n; |
| ... | ... | @@ -277,7 +256,7 @@ public: |
| 277 | 256 | } |
| 278 | 257 | |
| 279 | 258 | _LIBCPP_HIDE_FROM_ABI |
| 280 | constexpr __transform_view_iterator& operator-=(difference_type __n) | |
| 259 | constexpr __iterator& operator-=(difference_type __n) | |
| 281 | 260 | requires random_access_range<_Base> |
| 282 | 261 | { |
| 283 | 262 | __current_ -= __n; |
| ... | ... | @@ -293,77 +272,77 @@ public: |
| 293 | 272 | } |
| 294 | 273 | |
| 295 | 274 | _LIBCPP_HIDE_FROM_ABI |
| 296 | friend constexpr bool operator==(const __transform_view_iterator& __x, const __transform_view_iterator& __y) | |
| 275 | friend constexpr bool operator==(const __iterator& __x, const __iterator& __y) | |
| 297 | 276 | requires equality_comparable<iterator_t<_Base>> |
| 298 | 277 | { |
| 299 | 278 | return __x.__current_ == __y.__current_; |
| 300 | 279 | } |
| 301 | 280 | |
| 302 | 281 | _LIBCPP_HIDE_FROM_ABI |
| 303 | friend constexpr bool operator<(const __transform_view_iterator& __x, const __transform_view_iterator& __y) | |
| 282 | friend constexpr bool operator<(const __iterator& __x, const __iterator& __y) | |
| 304 | 283 | requires random_access_range<_Base> |
| 305 | 284 | { |
| 306 | 285 | return __x.__current_ < __y.__current_; |
| 307 | 286 | } |
| 308 | 287 | |
| 309 | 288 | _LIBCPP_HIDE_FROM_ABI |
| 310 | friend constexpr bool operator>(const __transform_view_iterator& __x, const __transform_view_iterator& __y) | |
| 289 | friend constexpr bool operator>(const __iterator& __x, const __iterator& __y) | |
| 311 | 290 | requires random_access_range<_Base> |
| 312 | 291 | { |
| 313 | 292 | return __x.__current_ > __y.__current_; |
| 314 | 293 | } |
| 315 | 294 | |
| 316 | 295 | _LIBCPP_HIDE_FROM_ABI |
| 317 | friend constexpr bool operator<=(const __transform_view_iterator& __x, const __transform_view_iterator& __y) | |
| 296 | friend constexpr bool operator<=(const __iterator& __x, const __iterator& __y) | |
| 318 | 297 | requires random_access_range<_Base> |
| 319 | 298 | { |
| 320 | 299 | return __x.__current_ <= __y.__current_; |
| 321 | 300 | } |
| 322 | 301 | |
| 323 | 302 | _LIBCPP_HIDE_FROM_ABI |
| 324 | friend constexpr bool operator>=(const __transform_view_iterator& __x, const __transform_view_iterator& __y) | |
| 303 | friend constexpr bool operator>=(const __iterator& __x, const __iterator& __y) | |
| 325 | 304 | requires random_access_range<_Base> |
| 326 | 305 | { |
| 327 | 306 | return __x.__current_ >= __y.__current_; |
| 328 | 307 | } |
| 329 | 308 | |
| 330 | 309 | _LIBCPP_HIDE_FROM_ABI |
| 331 | friend constexpr auto operator<=>(const __transform_view_iterator& __x, const __transform_view_iterator& __y) | |
| 310 | friend constexpr auto operator<=>(const __iterator& __x, const __iterator& __y) | |
| 332 | 311 | requires random_access_range<_Base> && three_way_comparable<iterator_t<_Base>> |
| 333 | 312 | { |
| 334 | 313 | return __x.__current_ <=> __y.__current_; |
| 335 | 314 | } |
| 336 | 315 | |
| 337 | 316 | _LIBCPP_HIDE_FROM_ABI |
| 338 | friend constexpr __transform_view_iterator operator+(__transform_view_iterator __i, difference_type __n) | |
| 317 | friend constexpr __iterator operator+(__iterator __i, difference_type __n) | |
| 339 | 318 | requires random_access_range<_Base> |
| 340 | 319 | { |
| 341 | return __transform_view_iterator{*__i.__parent_, __i.__current_ + __n}; | |
| 320 | return __iterator{*__i.__parent_, __i.__current_ + __n}; | |
| 342 | 321 | } |
| 343 | 322 | |
| 344 | 323 | _LIBCPP_HIDE_FROM_ABI |
| 345 | friend constexpr __transform_view_iterator operator+(difference_type __n, __transform_view_iterator __i) | |
| 324 | friend constexpr __iterator operator+(difference_type __n, __iterator __i) | |
| 346 | 325 | requires random_access_range<_Base> |
| 347 | 326 | { |
| 348 | return __transform_view_iterator{*__i.__parent_, __i.__current_ + __n}; | |
| 327 | return __iterator{*__i.__parent_, __i.__current_ + __n}; | |
| 349 | 328 | } |
| 350 | 329 | |
| 351 | 330 | _LIBCPP_HIDE_FROM_ABI |
| 352 | friend constexpr __transform_view_iterator operator-(__transform_view_iterator __i, difference_type __n) | |
| 331 | friend constexpr __iterator operator-(__iterator __i, difference_type __n) | |
| 353 | 332 | requires random_access_range<_Base> |
| 354 | 333 | { |
| 355 | return __transform_view_iterator{*__i.__parent_, __i.__current_ - __n}; | |
| 334 | return __iterator{*__i.__parent_, __i.__current_ - __n}; | |
| 356 | 335 | } |
| 357 | 336 | |
| 358 | 337 | _LIBCPP_HIDE_FROM_ABI |
| 359 | friend constexpr difference_type operator-(const __transform_view_iterator& __x, const __transform_view_iterator& __y) | |
| 338 | friend constexpr difference_type operator-(const __iterator& __x, const __iterator& __y) | |
| 360 | 339 | requires sized_sentinel_for<iterator_t<_Base>, iterator_t<_Base>> |
| 361 | 340 | { |
| 362 | 341 | return __x.__current_ - __y.__current_; |
| 363 | 342 | } |
| 364 | 343 | |
| 365 | 344 | _LIBCPP_HIDE_FROM_ABI |
| 366 | friend constexpr decltype(auto) iter_move(const __transform_view_iterator& __i) | |
| 345 | friend constexpr decltype(auto) iter_move(const __iterator& __i) | |
| 367 | 346 | noexcept(noexcept(*__i)) |
| 368 | 347 | { |
| 369 | 348 | if constexpr (is_lvalue_reference_v<decltype(*__i)>) |
| ... | ... | @@ -373,37 +352,33 @@ public: |
| 373 | 352 | } |
| 374 | 353 | }; |
| 375 | 354 | |
| 376 | template<input_range _View, copy_constructible _Fn, bool _Const> | |
| 355 | template<input_range _View, copy_constructible _Fn> | |
| 377 | 356 | requires __transform_view_constraints<_View, _Fn> |
| 378 | class __transform_view_sentinel { | |
| 379 | using _Parent = __maybe_const<_Const, transform_view<_View, _Fn>>; | |
| 357 | template<bool _Const> | |
| 358 | class transform_view<_View, _Fn>::__sentinel { | |
| 359 | using _Parent = __maybe_const<_Const, transform_view>; | |
| 380 | 360 | using _Base = __maybe_const<_Const, _View>; |
| 381 | 361 | |
| 382 | template <bool _IsConst> | |
| 383 | using __iterator = __transform_view_iterator<_View, _Fn, _IsConst>; | |
| 384 | ||
| 385 | 362 | sentinel_t<_Base> __end_ = sentinel_t<_Base>(); |
| 386 | 363 | |
| 387 | template<input_range _ViewType, copy_constructible _FunctionType, bool _IsConst> | |
| 388 | requires __transform_view_constraints<_ViewType, _FunctionType> | |
| 389 | friend class __transform_view_iterator; | |
| 364 | template<bool> | |
| 365 | friend class transform_view<_View, _Fn>::__iterator; | |
| 390 | 366 | |
| 391 | template<input_range _ViewType, copy_constructible _FunctionType, bool _IsConst> | |
| 392 | requires __transform_view_constraints<_ViewType, _FunctionType> | |
| 393 | friend class __transform_view_sentinel; | |
| 367 | template<bool> | |
| 368 | friend class transform_view<_View, _Fn>::__sentinel; | |
| 394 | 369 | |
| 395 | 370 | public: |
| 396 | 371 | _LIBCPP_HIDE_FROM_ABI |
| 397 | __transform_view_sentinel() = default; | |
| 372 | __sentinel() = default; | |
| 398 | 373 | |
| 399 | 374 | _LIBCPP_HIDE_FROM_ABI |
| 400 | constexpr explicit __transform_view_sentinel(sentinel_t<_Base> __end) : __end_(__end) {} | |
| 375 | constexpr explicit __sentinel(sentinel_t<_Base> __end) : __end_(__end) {} | |
| 401 | 376 | |
| 402 | // Note: `__i` should always be `__transform_view_sentinel<false>`, but directly using | |
| 403 | // `__transform_view_sentinel<false>` is ill-formed when `_Const` is false | |
| 377 | // Note: `__i` should always be `__sentinel<false>`, but directly using | |
| 378 | // `__sentinel<false>` is ill-formed when `_Const` is false | |
| 404 | 379 | // (see http://wg21.link/class.copy.ctor#5). |
| 405 | 380 | _LIBCPP_HIDE_FROM_ABI |
| 406 | constexpr __transform_view_sentinel(__transform_view_sentinel<_View, _Fn, !_Const> __i) | |
| 381 | constexpr __sentinel(__sentinel<!_Const> __i) | |
| 407 | 382 | requires _Const && convertible_to<sentinel_t<_View>, sentinel_t<_Base>> |
| 408 | 383 | : __end_(std::move(__i.__end_)) {} |
| 409 | 384 | |
| ... | ... | @@ -413,7 +388,7 @@ public: |
| 413 | 388 | template<bool _OtherConst> |
| 414 | 389 | requires sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 415 | 390 | _LIBCPP_HIDE_FROM_ABI |
| 416 | friend constexpr bool operator==(const __iterator<_OtherConst>& __x, const __transform_view_sentinel& __y) { | |
| 391 | friend constexpr bool operator==(const __iterator<_OtherConst>& __x, const __sentinel& __y) { | |
| 417 | 392 | return __x.__current_ == __y.__end_; |
| 418 | 393 | } |
| 419 | 394 | |
| ... | ... | @@ -421,7 +396,7 @@ public: |
| 421 | 396 | requires sized_sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 422 | 397 | _LIBCPP_HIDE_FROM_ABI |
| 423 | 398 | friend constexpr range_difference_t<__maybe_const<_OtherConst, _View>> |
| 424 | operator-(const __iterator<_OtherConst>& __x, const __transform_view_sentinel& __y) { | |
| 399 | operator-(const __iterator<_OtherConst>& __x, const __sentinel& __y) { | |
| 425 | 400 | return __x.__current_ - __y.__end_; |
| 426 | 401 | } |
| 427 | 402 | |
| ... | ... | @@ -429,7 +404,7 @@ public: |
| 429 | 404 | requires sized_sentinel_for<sentinel_t<_Base>, iterator_t<__maybe_const<_OtherConst, _View>>> |
| 430 | 405 | _LIBCPP_HIDE_FROM_ABI |
| 431 | 406 | friend constexpr range_difference_t<__maybe_const<_OtherConst, _View>> |
| 432 | operator-(const __transform_view_sentinel& __x, const __iterator<_OtherConst>& __y) { | |
| 407 | operator-(const __sentinel& __x, const __iterator<_OtherConst>& __y) { | |
| 433 | 408 | return __x.__end_ - __y.__current_; |
| 434 | 409 | } |
| 435 | 410 | }; |
lib/libcxx/include/__type_traits/add_pointer.h+2-2| ... | ... | @@ -22,7 +22,7 @@ |
| 22 | 22 | |
| 23 | 23 | _LIBCPP_BEGIN_NAMESPACE_STD |
| 24 | 24 | |
| 25 | #if __has_builtin(__add_pointer) | |
| 25 | #if !defined(_LIBCPP_WORKAROUND_OBJCXX_COMPILER_INTRINSICS) && __has_builtin(__add_pointer) | |
| 26 | 26 | |
| 27 | 27 | template <class _Tp> |
| 28 | 28 | using __add_pointer_t = __add_pointer(_Tp); |
| ... | ... | @@ -39,7 +39,7 @@ template <class _Tp> struct __add_pointer_impl<_Tp, false> |
| 39 | 39 | template <class _Tp> |
| 40 | 40 | using __add_pointer_t = typename __add_pointer_impl<_Tp>::type; |
| 41 | 41 | |
| 42 | #endif // __has_builtin(__add_pointer) | |
| 42 | #endif // !defined(_LIBCPP_WORKAROUND_OBJCXX_COMPILER_INTRINSICS) && __has_builtin(__add_pointer) | |
| 43 | 43 | |
| 44 | 44 | template <class _Tp> |
| 45 | 45 | struct add_pointer { |
lib/libcxx/include/__type_traits/remove_pointer.h+2-2| ... | ... | @@ -17,7 +17,7 @@ |
| 17 | 17 | |
| 18 | 18 | _LIBCPP_BEGIN_NAMESPACE_STD |
| 19 | 19 | |
| 20 | #if __has_builtin(__remove_pointer) | |
| 20 | #if !defined(_LIBCPP_WORKAROUND_OBJCXX_COMPILER_INTRINSICS) && __has_builtin(__remove_pointer) | |
| 21 | 21 | template <class _Tp> |
| 22 | 22 | struct remove_pointer { |
| 23 | 23 | using type _LIBCPP_NODEBUG = __remove_pointer(_Tp); |
| ... | ... | @@ -34,7 +34,7 @@ template <class _Tp> struct _LIBCPP_TEMPLATE_VIS remove_pointer<_Tp* const volat |
| 34 | 34 | |
| 35 | 35 | template <class _Tp> |
| 36 | 36 | using __remove_pointer_t = typename remove_pointer<_Tp>::type; |
| 37 | #endif // __has_builtin(__remove_pointer) | |
| 37 | #endif // !defined(_LIBCPP_WORKAROUND_OBJCXX_COMPILER_INTRINSICS) && __has_builtin(__remove_pointer) | |
| 38 | 38 | |
| 39 | 39 | #if _LIBCPP_STD_VER > 11 |
| 40 | 40 | template <class _Tp> using remove_pointer_t = __remove_pointer_t<_Tp>; |
lib/libcxx/include/any+5-5| ... | ... | @@ -175,7 +175,7 @@ namespace __any_imp |
| 175 | 175 | inline _LIBCPP_INLINE_VISIBILITY |
| 176 | 176 | bool __compare_typeid(type_info const* __id, const void* __fallback_id) |
| 177 | 177 | { |
| 178 | #if !defined(_LIBCPP_NO_RTTI) | |
| 178 | #if !defined(_LIBCPP_HAS_NO_RTTI) | |
| 179 | 179 | if (__id && *__id == typeid(_Tp)) |
| 180 | 180 | return true; |
| 181 | 181 | #endif |
| ... | ... | @@ -294,7 +294,7 @@ public: |
| 294 | 294 | _LIBCPP_INLINE_VISIBILITY |
| 295 | 295 | bool has_value() const _NOEXCEPT { return __h_ != nullptr; } |
| 296 | 296 | |
| 297 | #if !defined(_LIBCPP_NO_RTTI) | |
| 297 | #if !defined(_LIBCPP_HAS_NO_RTTI) | |
| 298 | 298 | _LIBCPP_INLINE_VISIBILITY |
| 299 | 299 | const type_info & type() const _NOEXCEPT { |
| 300 | 300 | if (__h_) { |
| ... | ... | @@ -426,7 +426,7 @@ namespace __any_imp |
| 426 | 426 | _LIBCPP_INLINE_VISIBILITY |
| 427 | 427 | static void* __type_info() |
| 428 | 428 | { |
| 429 | #if !defined(_LIBCPP_NO_RTTI) | |
| 429 | #if !defined(_LIBCPP_HAS_NO_RTTI) | |
| 430 | 430 | return const_cast<void*>(static_cast<void const *>(&typeid(_Tp))); |
| 431 | 431 | #else |
| 432 | 432 | return nullptr; |
| ... | ... | @@ -514,7 +514,7 @@ namespace __any_imp |
| 514 | 514 | _LIBCPP_INLINE_VISIBILITY |
| 515 | 515 | static void* __type_info() |
| 516 | 516 | { |
| 517 | #if !defined(_LIBCPP_NO_RTTI) | |
| 517 | #if !defined(_LIBCPP_HAS_NO_RTTI) | |
| 518 | 518 | return const_cast<void*>(static_cast<void const *>(&typeid(_Tp))); |
| 519 | 519 | #else |
| 520 | 520 | return nullptr; |
| ... | ... | @@ -680,7 +680,7 @@ any_cast(any * __any) _NOEXCEPT |
| 680 | 680 | typedef add_pointer_t<_ValueType> _ReturnType; |
| 681 | 681 | if (__any && __any->__h_) { |
| 682 | 682 | void *__p = __any->__call(_Action::_Get, nullptr, |
| 683 | #if !defined(_LIBCPP_NO_RTTI) | |
| 683 | #if !defined(_LIBCPP_HAS_NO_RTTI) | |
| 684 | 684 | &typeid(_ValueType), |
| 685 | 685 | #else |
| 686 | 686 | nullptr, |
lib/libcxx/include/version+2| ... | ... | @@ -139,6 +139,7 @@ __cpp_lib_polymorphic_allocator 201902L <memory_resource |
| 139 | 139 | __cpp_lib_quoted_string_io 201304L <iomanip> |
| 140 | 140 | __cpp_lib_ranges 202106L <algorithm> <functional> <iterator> |
| 141 | 141 | <memory> <ranges> |
| 142 | __cpp_lib_ranges_as_rvalue 202207L <ranges> | |
| 142 | 143 | __cpp_lib_ranges_chunk 202202L <ranges> |
| 143 | 144 | __cpp_lib_ranges_chunk_by 202202L <ranges> |
| 144 | 145 | __cpp_lib_ranges_iota 202202L <numeric> |
| ... | ... | @@ -401,6 +402,7 @@ __cpp_lib_void_t 201411L <type_traits> |
| 401 | 402 | # undef __cpp_lib_optional |
| 402 | 403 | # define __cpp_lib_optional 202110L |
| 403 | 404 | // # define __cpp_lib_out_ptr 202106L |
| 405 | # define __cpp_lib_ranges_as_rvalue 202207L | |
| 404 | 406 | // # define __cpp_lib_ranges_chunk 202202L |
| 405 | 407 | // # define __cpp_lib_ranges_chunk_by 202202L |
| 406 | 408 | // # define __cpp_lib_ranges_iota 202202L |