[libcxx-commits] [libcxx] [libc++][ranges] Implement LWG3904: `lazy_split_view::outer-iterator`'s const-converting constructor isn't setting `trailing_empty_` (PR #237550)

via libcxx-commits libcxx-commits at lists.llvm.org
Sat Oct 31 04:13:45 PDT 2026


llvmorg-github-actions[bot] wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-libcxx

Author: R. Aoto (aotodev)

<details>
<summary>Changes</summary>

Copy `trailing_empty_` in `outer-iterator`'s const-converting constructor. Previously, converting an iterator that points at the trailing empty subrange (e.g. the second element of `"a,"` split by `","`) made it compare equal to `default_sentinel`, so that subrange was lost.

Fixes #<!-- -->105276


---
Full diff: https://github.com/llvm/llvm-project/pull/237550.diff


3 Files Affected:

- (modified) libcxx/docs/Status/Cxx26Issues.csv (+1-1) 
- (modified) libcxx/include/__ranges/lazy_split_view.h (+1-1) 
- (modified) libcxx/test/std/ranges/range.adaptors/range.lazy.split/range.lazy.split.outer/ctor.copy.pass.cpp (+13) 


``````````diff
diff --git a/libcxx/docs/Status/Cxx26Issues.csv b/libcxx/docs/Status/Cxx26Issues.csv
index 638f7a4e6ffa1..9ff096c888b97 100644
--- a/libcxx/docs/Status/Cxx26Issues.csv
+++ b/libcxx/docs/Status/Cxx26Issues.csv
@@ -6,7 +6,7 @@
 "`LWG3893 <https://wg21.link/LWG3893>`__","LWG 3661 broke ``atomic<shared_ptr<T>> a; a = nullptr;``","2023-06 (Varna)","","","`#105273 <https://github.com/llvm/llvm-project/issues/105273>`__",""
 "`LWG3894 <https://wg21.link/LWG3894>`__","``generator::promise_type::yield_value(ranges::elements_of<Rng, Alloc>)`` should not be ``noexcept``","2023-06 (Varna)","","","`#105274 <https://github.com/llvm/llvm-project/issues/105274>`__",""
 "`LWG3903 <https://wg21.link/LWG3903>`__","span destructor is redundantly noexcept","2023-06 (Varna)","|Complete|","7","`#105275 <https://github.com/llvm/llvm-project/issues/105275>`__",""
-"`LWG3904 <https://wg21.link/LWG3904>`__","``lazy_split_view::outer-iterator``'s const-converting constructor isn't setting ``trailing_empty_``","2023-06 (Varna)","","","`#105276 <https://github.com/llvm/llvm-project/issues/105276>`__",""
+"`LWG3904 <https://wg21.link/LWG3904>`__","``lazy_split_view::outer-iterator``'s const-converting constructor isn't setting ``trailing_empty_``","2023-06 (Varna)","|Complete|","24","`#105276 <https://github.com/llvm/llvm-project/issues/105276>`__",""
 "`LWG3905 <https://wg21.link/LWG3905>`__","Type of ``std::fexcept_t``","2023-06 (Varna)","|Complete|","3.4","`#105277 <https://github.com/llvm/llvm-project/issues/105277>`__",""
 "`LWG3912 <https://wg21.link/LWG3912>`__","``enumerate_view::iterator::operator-`` should be ``noexcept``","2023-06 (Varna)","|Complete|","23","`#105279 <https://github.com/llvm/llvm-project/issues/105279>`__",""
 "`LWG3914 <https://wg21.link/LWG3914>`__","Inconsistent template-head of ``ranges::enumerate_view``","2023-06 (Varna)","|Complete|","23","`#105280 <https://github.com/llvm/llvm-project/issues/105280>`__",""
diff --git a/libcxx/include/__ranges/lazy_split_view.h b/libcxx/include/__ranges/lazy_split_view.h
index 468f9714318c1..f359d6ab9a351 100644
--- a/libcxx/include/__ranges/lazy_split_view.h
+++ b/libcxx/include/__ranges/lazy_split_view.h
@@ -209,7 +209,7 @@ class lazy_split_view : public view_interface<lazy_split_view<_View, _Pattern>>
 
     _LIBCPP_HIDE_FROM_ABI constexpr __outer_iterator(__outer_iterator<!_Const> __i)
       requires _Const && convertible_to<iterator_t<_View>, iterator_t<_Base>>
-        : __parent_(__i.__parent_), __current_(std::move(__i.__current_)) {}
+        : __parent_(__i.__parent_), __current_(std::move(__i.__current_)), __trailing_empty_(__i.__trailing_empty_) {}
 
     [[nodiscard]] _LIBCPP_HIDE_FROM_ABI constexpr value_type operator*() const { return value_type{*this}; }
 
diff --git a/libcxx/test/std/ranges/range.adaptors/range.lazy.split/range.lazy.split.outer/ctor.copy.pass.cpp b/libcxx/test/std/ranges/range.adaptors/range.lazy.split/range.lazy.split.outer/ctor.copy.pass.cpp
index a4f87914575e0..14ff57ddeca8f 100644
--- a/libcxx/test/std/ranges/range.adaptors/range.lazy.split/range.lazy.split.outer/ctor.copy.pass.cpp
+++ b/libcxx/test/std/ranges/range.adaptors/range.lazy.split/range.lazy.split.outer/ctor.copy.pass.cpp
@@ -13,6 +13,7 @@
 
 #include <ranges>
 
+#include <cassert>
 #include <string_view>
 #include <type_traits>
 #include <utility>
@@ -42,6 +43,18 @@ static_assert(!std::is_constructible_v<OuterIterNonConst, OuterIterConst>);
 constexpr bool test() {
   [[maybe_unused]] OuterIterConst i(OuterIterNonConst{});
 
+  // LWG3904: the converting constructor copies trailing_empty_.
+  {
+    SplitViewDiff v("a,", ",");
+    auto it = v.begin();
+    ++it;
+
+    OuterIterConst cit = std::move(it);
+    assert(cit != std::default_sentinel);
+    ++cit;
+    assert(cit == std::default_sentinel);
+  }
+
   return true;
 }
 

``````````

</details>


https://github.com/llvm/llvm-project/pull/237550


More information about the libcxx-commits mailing list