//===----------------------------------------------------------------------===// // // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. // See https://llvm.org/LICENSE.txt for license information. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception // //===----------------------------------------------------------------------===// // UNSUPPORTED: c++03, c++11, c++14, c++17 // template // requires sentinel_for, iterator_t>> // friend constexpr bool operator==(const iterator& x, const sentinel& y); #include #include #include #include #include #include "../types.h" #include "test_range.h" using Iterator = random_access_iterator*>; using ConstIterator = random_access_iterator*>; template struct ConstComparableSentinel { using Iter = std::conditional_t; Iter iter_; explicit ConstComparableSentinel() = default; constexpr explicit ConstComparableSentinel(const Iter& it) : iter_(it) {} constexpr friend bool operator==(const Iterator& i, const ConstComparableSentinel& s) { return base(i) == base(s.iter_); } constexpr friend bool operator==(const ConstIterator& i, const ConstComparableSentinel& s) { return base(i) == base(s.iter_); } }; struct ConstComparableView : BufferView*> { using BufferView*>::BufferView; constexpr auto begin() { return Iterator(data_); } constexpr auto begin() const { return ConstIterator(data_); } constexpr auto end() { return ConstComparableSentinel(Iterator(data_ + size_)); } constexpr auto end() const { return ConstComparableSentinel(ConstIterator(data_ + size_)); } }; static_assert(weakly_equality_comparable_with, std::ranges::sentinel_t>); static_assert(weakly_equality_comparable_with, std::ranges::sentinel_t>); constexpr bool test() { int buffer[4][4] = {{1111, 2222, 3333, 4444}, {555, 666, 777, 888}, {99, 1010, 1111, 1212}, {13, 14, 15, 16}}; // test iterator == sentinel { ChildView children[4] = {ChildView(buffer[0]), ChildView(buffer[1]), ChildView(buffer[2]), ChildView(buffer[3])}; auto jv = std::ranges::join_view(ParentView(children)); assert(jv.end() == std::ranges::next(jv.begin(), 16)); } // test iterator == sentinel { ChildView children[4] = {ChildView(buffer[0]), ChildView(buffer[1]), ChildView(buffer[2]), ChildView(buffer[3])}; using ParentT = std::remove_all_extents_t; auto jv = std::ranges::join_view(ForwardParentView(children)); assert(std::as_const(jv).end() == std::ranges::next(jv.begin(), 16)); } // test iterator == sentinel { CopyableChild children[4] = {CopyableChild(buffer[0]), CopyableChild(buffer[1]), CopyableChild(buffer[2]), CopyableChild(buffer[3])}; using ParentT = std::remove_all_extents_t; const auto jv = std::ranges::join_view(ForwardParentView(children)); assert(jv.end() == std::ranges::next(jv.begin(), 16)); } // test iterator == sentinel { BufferView inners[] = {buffer[0], buffer[1]}; ConstComparableView outer(inners); auto jv = std::ranges::join_view(outer); assert(jv.end() == std::ranges::next(jv.begin(), 8)); assert(std::as_const(jv).end() == std::ranges::next(jv.begin(), 8)); assert(jv.end() == std::ranges::next(std::as_const(jv).begin(), 8)); } return true; } int main(int, char**) { test(); static_assert(test()); return 0; }