[libcxx-commits] [libcxx] [libc++] Implement `ranges::fold_left_first` and `ranges::fold_left_first_with_iter` (PR #180214)
Connector Switch via libcxx-commits
libcxx-commits at lists.llvm.org
Fri Feb 6 07:51:53 PST 2026
================
@@ -126,6 +130,63 @@ struct __fold_left {
};
inline constexpr auto fold_left = __fold_left();
+
+struct __fold_left_first_with_iter {
+ template <input_iterator _Iter,
+ sentinel_for<_Iter> _Sent,
+ __indirectly_binary_left_foldable<iter_value_t<_Iter>, _Iter> _Func>
+ requires constructible_from<iter_value_t<_Iter>, iter_reference_t<_Iter>>
+ [[nodiscard]] _LIBCPP_HIDE_FROM_ABI static constexpr auto operator()(_Iter __first, _Sent __last, _Func __func) {
+ using _Up = decltype(fold_left(std::move(__first), __last, iter_value_t<_Iter>(*__first), __func));
+
+ if (__first == __last)
+ return fold_left_first_with_iter_result<_Iter, optional<_Up>>{std::move(__first), optional<_Up>()};
+
+ _Up __result(*__first);
+ ++__first;
+ __identity __proj;
+ auto __end = std::__for_each(
+ std::move(__first),
+ std::move(__last),
+ [&](auto&& __element) {
+ __result = std::invoke(__func, std::move(__result), std::forward<decltype(__element)>(__element));
+ },
+ __proj);
+
+ return fold_left_first_with_iter_result<_Iter, optional<_Up>>{std::move(__end), optional<_Up>(std::move(__result))};
+ }
+
+ template <input_range _Range, __indirectly_binary_left_foldable<range_value_t<_Range>, iterator_t<_Range>> _Func>
+ requires constructible_from<range_value_t<_Range>, range_reference_t<_Range>>
+ [[nodiscard]] _LIBCPP_HIDE_FROM_ABI static constexpr auto operator()(_Range&& __range, _Func __func) {
+ auto __result = operator()(ranges::begin(__range), ranges::end(__range), std::ref(__func));
+
+ using _Up = decltype(fold_left(
+ ranges::begin(__range), ranges::end(__range), range_value_t<_Range>(*ranges::begin(__range)), __func));
+ return fold_left_first_with_iter_result<borrowed_iterator_t<_Range>, optional<_Up>>{
+ std::move(__result.in), std::move(__result.value)};
+ }
----------------
c8ef wrote:
This logic is necessary as per standards, otherwise the rvalue range test will fail.
https://github.com/llvm/llvm-project/pull/180214
More information about the libcxx-commits
mailing list