1 //===----------------------------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #ifndef TEST_STD_RANGES_RANGE_ADAPTORS_RANGE_ZIP_TYPES_H
10 #define TEST_STD_RANGES_RANGE_ADAPTORS_RANGE_ZIP_TYPES_H
11 
12 #include <functional>
13 #include <ranges>
14 
15 #include "test_macros.h"
16 #include "test_iterators.h"
17 #include "test_range.h"
18 
19 #if TEST_STD_VER <= 20
20 #  error "range.zip/types.h" can only be included in builds supporting C++20
21 #endif // TEST_STD_VER <= 20
22 
23 template <class T>
24 struct BufferView : std::ranges::view_base {
25   T* buffer_;
26   std::size_t size_;
27 
28   template <std::size_t N>
BufferViewBufferView29   constexpr BufferView(T (&b)[N]) : buffer_(b), size_(N) {}
30 };
31 
32 using IntBufferView = BufferView<int>;
33 
34 template <bool Simple>
35 struct Common :  IntBufferView {
36   using IntBufferView::IntBufferView;
37 
beginCommon38   constexpr int* begin()
39     requires(!Simple)
40   {
41     return buffer_;
42   }
beginCommon43   constexpr const int* begin() const { return buffer_; }
endCommon44   constexpr int* end()
45     requires(!Simple)
46   {
47     return buffer_ + size_;
48   }
endCommon49   constexpr const int* end() const { return buffer_ + size_; }
50 };
51 using SimpleCommon = Common<true>;
52 using NonSimpleCommon = Common<false>;
53 
54 using SimpleCommonRandomAccessSized = SimpleCommon;
55 using NonSimpleCommonRandomAccessSized = NonSimpleCommon;
56 
57 static_assert(std::ranges::common_range<Common<true>>);
58 static_assert(std::ranges::random_access_range<SimpleCommon>);
59 static_assert(std::ranges::sized_range<SimpleCommon>);
60 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<SimpleCommon>);
61 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleCommon>);
62 
63 template <bool Simple>
64 struct CommonNonRandom : IntBufferView {
65   using IntBufferView::IntBufferView;
66   using const_iterator = forward_iterator<const int*>;
67   using iterator = forward_iterator<int*>;
beginCommonNonRandom68   constexpr iterator begin()
69     requires(!Simple) {
70     return iterator(buffer_);
71   }
beginCommonNonRandom72   constexpr const_iterator begin() const { return const_iterator(buffer_); }
endCommonNonRandom73   constexpr iterator end()
74     requires(!Simple) {
75     return iterator(buffer_ + size_);
76   }
endCommonNonRandom77   constexpr const_iterator end() const { return const_iterator(buffer_ + size_); }
78 };
79 
80 using SimpleCommonNonRandom = CommonNonRandom<true>;
81 using NonSimpleCommonNonRandom = CommonNonRandom<false>;
82 
83 static_assert(std::ranges::common_range<SimpleCommonNonRandom>);
84 static_assert(!std::ranges::random_access_range<SimpleCommonNonRandom>);
85 static_assert(!std::ranges::sized_range<SimpleCommonNonRandom>);
86 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<SimpleCommonNonRandom>);
87 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleCommonNonRandom>);
88 
89 template <bool Simple>
90 struct NonCommon : IntBufferView {
91   using IntBufferView::IntBufferView;
beginNonCommon92   constexpr int* begin()
93     requires(!Simple) {
94     return buffer_;
95   }
beginNonCommon96   constexpr const int* begin() const { return buffer_; }
endNonCommon97   constexpr sentinel_wrapper<int*> end()
98     requires(!Simple) {
99     return sentinel_wrapper<int*>(buffer_ + size_);
100   }
endNonCommon101   constexpr sentinel_wrapper<const int*> end() const { return sentinel_wrapper<const int*>(buffer_ + size_); }
102 };
103 
104 using SimpleNonCommon = NonCommon<true>;
105 using NonSimpleNonCommon = NonCommon<false>;
106 
107 static_assert(!std::ranges::common_range<SimpleNonCommon>);
108 static_assert(std::ranges::random_access_range<SimpleNonCommon>);
109 static_assert(!std::ranges::sized_range<SimpleNonCommon>);
110 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<SimpleNonCommon>);
111 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleNonCommon>);
112 
113 template <bool Simple>
114 struct NonCommonSized : IntBufferView {
115   using IntBufferView::IntBufferView;
beginNonCommonSized116   constexpr int* begin()
117     requires(!Simple) {
118     return buffer_;
119   }
beginNonCommonSized120   constexpr const int* begin() const { return buffer_; }
endNonCommonSized121   constexpr sentinel_wrapper<int*> end()
122     requires(!Simple) {
123     return sentinel_wrapper<int*>(buffer_ + size_);
124   }
endNonCommonSized125   constexpr sentinel_wrapper<const int*> end() const { return sentinel_wrapper<const int*>(buffer_ + size_); }
sizeNonCommonSized126   constexpr std::size_t size() const { return size_; }
127 };
128 
129 using SimpleNonCommonSized = NonCommonSized<true>;
130 using SimpleNonCommonRandomAcessSized = SimpleNonCommonSized;
131 using NonSimpleNonCommonSized = NonCommonSized<false>;
132 using NonSimpleNonCommonRandomAcessSized = NonSimpleNonCommonSized;
133 
134 static_assert(!std::ranges::common_range<SimpleNonCommonSized>);
135 static_assert(std::ranges::random_access_range<SimpleNonCommonSized>);
136 static_assert(std::ranges::sized_range<SimpleNonCommonSized>);
137 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<SimpleNonCommonSized>);
138 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleNonCommonSized>);
139 
140 template <bool Simple>
141 struct NonCommonNonRandom : IntBufferView {
142   using IntBufferView::IntBufferView;
143 
144   using const_iterator = forward_iterator<const int*>;
145   using iterator = forward_iterator<int*>;
146 
beginNonCommonNonRandom147   constexpr iterator begin()
148     requires(!Simple) {
149     return iterator(buffer_);
150   }
beginNonCommonNonRandom151   constexpr const_iterator begin() const { return const_iterator(buffer_); }
endNonCommonNonRandom152   constexpr sentinel_wrapper<iterator> end()
153     requires(!Simple) {
154     return sentinel_wrapper<iterator>(iterator(buffer_ + size_));
155   }
endNonCommonNonRandom156   constexpr sentinel_wrapper<const_iterator> end() const {
157     return sentinel_wrapper<const_iterator>(const_iterator(buffer_ + size_));
158   }
159 };
160 
161 using SimpleNonCommonNonRandom = NonCommonNonRandom<true>;
162 using NonSimpleNonCommonNonRandom = NonCommonNonRandom<false>;
163 
164 static_assert(!std::ranges::common_range<SimpleNonCommonNonRandom>);
165 static_assert(!std::ranges::random_access_range<SimpleNonCommonNonRandom>);
166 static_assert(!std::ranges::sized_range<SimpleNonCommonNonRandom>);
167 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<SimpleNonCommonNonRandom>);
168 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleNonCommonNonRandom>);
169 
170 template <class Iter, class Sent = Iter, class NonConstIter = Iter, class NonConstSent = Sent>
171 struct BasicView : IntBufferView {
172   using IntBufferView::IntBufferView;
173 
beginBasicView174   constexpr NonConstIter begin()
175     requires(!std::is_same_v<Iter, NonConstIter>) {
176     return NonConstIter(buffer_);
177   }
beginBasicView178   constexpr Iter begin() const { return Iter(buffer_); }
179 
endBasicView180   constexpr NonConstSent end()
181     requires(!std::is_same_v<Sent, NonConstSent>) {
182     if constexpr (std::is_same_v<NonConstIter, NonConstSent>) {
183       return NonConstIter(buffer_ + size_);
184     } else {
185       return NonConstSent(NonConstIter(buffer_ + size_));
186     }
187   }
188 
endBasicView189   constexpr Sent end() const {
190     if constexpr (std::is_same_v<Iter, Sent>) {
191       return Iter(buffer_ + size_);
192     } else {
193       return Sent(Iter(buffer_ + size_));
194     }
195   }
196 };
197 
198 template <class Base = int*>
199 struct forward_sized_iterator {
200   Base it_ = nullptr;
201 
202   using iterator_category = std::forward_iterator_tag;
203   using value_type = int;
204   using difference_type = intptr_t;
205   using pointer = Base;
206   using reference = decltype(*Base{});
207 
208   forward_sized_iterator() = default;
forward_sized_iteratorforward_sized_iterator209   constexpr forward_sized_iterator(Base it) : it_(it) {}
210 
211   constexpr reference operator*() const { return *it_; }
212 
213   constexpr forward_sized_iterator& operator++() {
214     ++it_;
215     return *this;
216   }
217   constexpr forward_sized_iterator operator++(int) { return forward_sized_iterator(it_++); }
218 
219   friend constexpr bool operator==(const forward_sized_iterator&, const forward_sized_iterator&) = default;
220 
221   friend constexpr difference_type operator-(const forward_sized_iterator& x, const forward_sized_iterator& y) {
222     return x.it_ - y.it_;
223   }
224 };
225 static_assert(std::forward_iterator<forward_sized_iterator<>>);
226 static_assert(std::sized_sentinel_for<forward_sized_iterator<>, forward_sized_iterator<>>);
227 
228 using ForwardSizedView = BasicView<forward_sized_iterator<>>;
229 static_assert(std::ranges::forward_range<ForwardSizedView>);
230 static_assert(std::ranges::sized_range<ForwardSizedView>);
231 static_assert(std::ranges::common_range<ForwardSizedView>);
232 static_assert(!std::ranges::random_access_range<ForwardSizedView>);
233 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<ForwardSizedView>);
234 
235 using NonSimpleForwardSizedView = BasicView<forward_sized_iterator<const int*>, forward_sized_iterator<const int*>,
236                                             forward_sized_iterator<int*>, forward_sized_iterator<int*>>;
237 static_assert(std::ranges::forward_range<NonSimpleForwardSizedView>);
238 static_assert(std::ranges::sized_range<NonSimpleForwardSizedView>);
239 static_assert(std::ranges::common_range<NonSimpleForwardSizedView>);
240 static_assert(!std::ranges::random_access_range<NonSimpleForwardSizedView>);
241 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleForwardSizedView>);
242 
243 using ForwardSizedNonCommon = BasicView<forward_sized_iterator<>, sized_sentinel<forward_sized_iterator<>>>;
244 static_assert(std::ranges::forward_range<ForwardSizedNonCommon>);
245 static_assert(std::ranges::sized_range<ForwardSizedNonCommon>);
246 static_assert(!std::ranges::common_range<ForwardSizedNonCommon>);
247 static_assert(!std::ranges::random_access_range<ForwardSizedNonCommon>);
248 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<ForwardSizedNonCommon>);
249 
250 using NonSimpleForwardSizedNonCommon =
251     BasicView<forward_sized_iterator<const int*>, sized_sentinel<forward_sized_iterator<const int*>>,
252               forward_sized_iterator<int*>, sized_sentinel<forward_sized_iterator<int*>>>;
253 static_assert(std::ranges::forward_range<NonSimpleForwardSizedNonCommon>);
254 static_assert(std::ranges::sized_range<NonSimpleForwardSizedNonCommon>);
255 static_assert(!std::ranges::common_range<NonSimpleForwardSizedNonCommon>);
256 static_assert(!std::ranges::random_access_range<NonSimpleForwardSizedNonCommon>);
257 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleForwardSizedNonCommon>);
258 
259 struct SizedRandomAccessView : IntBufferView {
260   using IntBufferView::IntBufferView;
261   using iterator = random_access_iterator<int*>;
262 
beginSizedRandomAccessView263   constexpr auto begin() const { return iterator(buffer_); }
endSizedRandomAccessView264   constexpr auto end() const { return sized_sentinel<iterator>(iterator(buffer_ + size_)); }
265 
decltypeSizedRandomAccessView266   constexpr decltype(auto) operator[](std::size_t n) const { return *(begin() + n); }
267 };
268 static_assert(std::ranges::view<SizedRandomAccessView>);
269 static_assert(std::ranges::random_access_range<SizedRandomAccessView>);
270 static_assert(std::ranges::sized_range<SizedRandomAccessView>);
271 
272 using NonSizedRandomAccessView =
273     BasicView<random_access_iterator<int*>, sentinel_wrapper<random_access_iterator<int*>>>;
274 static_assert(!std::ranges::contiguous_range<NonSizedRandomAccessView>);
275 static_assert(std::ranges::random_access_range<SizedRandomAccessView>);
276 static_assert(!std::ranges::common_range<NonSizedRandomAccessView>);
277 static_assert(!std::ranges::sized_range<NonSizedRandomAccessView>);
278 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<NonSizedRandomAccessView>);
279 
280 using NonSimpleNonSizedRandomAccessView =
281     BasicView<random_access_iterator<const int*>, sentinel_wrapper<random_access_iterator<const int*>>,
282               random_access_iterator<int*>, sentinel_wrapper<random_access_iterator<int*>> >;
283 static_assert(!std::ranges::contiguous_range<NonSimpleNonSizedRandomAccessView>);
284 static_assert(std::ranges::random_access_range<NonSimpleNonSizedRandomAccessView>);
285 static_assert(!std::ranges::common_range<NonSimpleNonSizedRandomAccessView>);
286 static_assert(!std::ranges::sized_range<NonSimpleNonSizedRandomAccessView>);
287 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleNonSizedRandomAccessView>);
288 
289 using ContiguousCommonView = BasicView<int*>;
290 static_assert(std::ranges::contiguous_range<ContiguousCommonView>);
291 static_assert(std::ranges::common_range<ContiguousCommonView>);
292 static_assert(std::ranges::sized_range<ContiguousCommonView>);
293 
294 using ContiguousNonCommonView = BasicView<int*, sentinel_wrapper<int*>>;
295 static_assert(std::ranges::contiguous_range<ContiguousNonCommonView>);
296 static_assert(!std::ranges::common_range<ContiguousNonCommonView>);
297 static_assert(!std::ranges::sized_range<ContiguousNonCommonView>);
298 
299 using ContiguousNonCommonSized = BasicView<int*, sized_sentinel<int*>>;
300 
301 static_assert(std::ranges::contiguous_range<ContiguousNonCommonSized>);
302 static_assert(!std::ranges::common_range<ContiguousNonCommonSized>);
303 static_assert(std::ranges::sized_range<ContiguousNonCommonSized>);
304 
305 template <class Base = int*>
306 struct common_input_iterator {
307   Base it_;
308 
309   using value_type = int;
310   using difference_type = std::intptr_t;
311   using iterator_concept = std::input_iterator_tag;
312 
313   constexpr common_input_iterator() = default;
common_input_iteratorcommon_input_iterator314   constexpr explicit common_input_iterator(Base it) : it_(it) {}
315 
316   constexpr common_input_iterator& operator++() {
317     ++it_;
318     return *this;
319   }
320   constexpr void operator++(int) { ++it_; }
321 
322   constexpr int& operator*() const { return *it_; }
323 
324   friend constexpr bool operator==(common_input_iterator const&, common_input_iterator const&) = default;
325 };
326 
327 using InputCommonView = BasicView<common_input_iterator<>>;
328 static_assert(std::ranges::input_range<InputCommonView>);
329 static_assert(!std::ranges::forward_range<InputCommonView>);
330 static_assert(std::ranges::common_range<InputCommonView>);
331 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<InputCommonView>);
332 
333 using NonSimpleInputCommonView = BasicView<common_input_iterator<const int*>, common_input_iterator<const int*>,
334                                            common_input_iterator<int*>, common_input_iterator<int*>>;
335 static_assert(std::ranges::input_range<NonSimpleInputCommonView>);
336 static_assert(!std::ranges::forward_range<NonSimpleInputCommonView>);
337 static_assert(std::ranges::common_range<NonSimpleInputCommonView>);
338 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleInputCommonView>);
339 
340 using InputNonCommonView = BasicView<common_input_iterator<>, sentinel_wrapper<common_input_iterator<>>>;
341 static_assert(std::ranges::input_range<InputNonCommonView>);
342 static_assert(!std::ranges::forward_range<InputNonCommonView>);
343 static_assert(!std::ranges::common_range<InputNonCommonView>);
344 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<InputNonCommonView>);
345 
346 using NonSimpleInputNonCommonView =
347     BasicView<common_input_iterator<const int*>, sentinel_wrapper<common_input_iterator<const int*>>,
348               common_input_iterator<int*>, sentinel_wrapper<common_input_iterator<int*>>>;
349 static_assert(std::ranges::input_range<InputNonCommonView>);
350 static_assert(!std::ranges::forward_range<InputNonCommonView>);
351 static_assert(!std::ranges::common_range<InputNonCommonView>);
352 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleInputNonCommonView>);
353 
354 using BidiCommonView = BasicView<bidirectional_iterator<int*>>;
355 static_assert(!std::ranges::sized_range<BidiCommonView>);
356 static_assert(std::ranges::bidirectional_range<BidiCommonView>);
357 static_assert(!std::ranges::random_access_range<BidiCommonView>);
358 static_assert(std::ranges::common_range<BidiCommonView>);
359 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<BidiCommonView>);
360 
361 using NonSimpleBidiCommonView = BasicView<bidirectional_iterator<const int*>, bidirectional_iterator<const int*>,
362                                           bidirectional_iterator<int*>, bidirectional_iterator<int*>>;
363 static_assert(!std::ranges::sized_range<NonSimpleBidiCommonView>);
364 static_assert(std::ranges::bidirectional_range<NonSimpleBidiCommonView>);
365 static_assert(!std::ranges::random_access_range<NonSimpleBidiCommonView>);
366 static_assert(std::ranges::common_range<NonSimpleBidiCommonView>);
367 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleBidiCommonView>);
368 
369 struct SizedBidiCommon : BidiCommonView {
370   using BidiCommonView::BidiCommonView;
sizeSizedBidiCommon371   std::size_t size() const { return base(end()) - base(begin()); }
372 };
373 static_assert(std::ranges::sized_range<SizedBidiCommon>);
374 static_assert(std::ranges::bidirectional_range<SizedBidiCommon>);
375 static_assert(!std::ranges::random_access_range<SizedBidiCommon>);
376 static_assert(std::ranges::common_range<SizedBidiCommon>);
377 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<SizedBidiCommon>);
378 
379 struct NonSimpleSizedBidiCommon : NonSimpleBidiCommonView {
380   using NonSimpleBidiCommonView::NonSimpleBidiCommonView;
sizeNonSimpleSizedBidiCommon381   std::size_t size() const { return base(end()) - base(begin()); }
382 };
383 static_assert(std::ranges::sized_range<NonSimpleSizedBidiCommon>);
384 static_assert(std::ranges::bidirectional_range<NonSimpleSizedBidiCommon>);
385 static_assert(!std::ranges::random_access_range<NonSimpleSizedBidiCommon>);
386 static_assert(std::ranges::common_range<NonSimpleSizedBidiCommon>);
387 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleSizedBidiCommon>);
388 
389 using BidiNonCommonView = BasicView<bidirectional_iterator<int*>, sentinel_wrapper<bidirectional_iterator<int*>>>;
390 static_assert(!std::ranges::sized_range<BidiNonCommonView>);
391 static_assert(std::ranges::bidirectional_range<BidiNonCommonView>);
392 static_assert(!std::ranges::random_access_range<BidiNonCommonView>);
393 static_assert(!std::ranges::common_range<BidiNonCommonView>);
394 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<BidiNonCommonView>);
395 
396 using NonSimpleBidiNonCommonView =
397     BasicView<bidirectional_iterator<const int*>, sentinel_wrapper<bidirectional_iterator<const int*>>,
398               bidirectional_iterator<int*>, sentinel_wrapper<bidirectional_iterator<int*>>>;
399 static_assert(!std::ranges::sized_range<NonSimpleBidiNonCommonView>);
400 static_assert(std::ranges::bidirectional_range<NonSimpleBidiNonCommonView>);
401 static_assert(!std::ranges::random_access_range<NonSimpleBidiNonCommonView>);
402 static_assert(!std::ranges::common_range<NonSimpleBidiNonCommonView>);
403 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleBidiNonCommonView>);
404 
405 using SizedBidiNonCommonView = BasicView<bidirectional_iterator<int*>, sized_sentinel<bidirectional_iterator<int*>>>;
406 static_assert(std::ranges::sized_range<SizedBidiNonCommonView>);
407 static_assert(std::ranges::bidirectional_range<SizedBidiNonCommonView>);
408 static_assert(!std::ranges::random_access_range<SizedBidiNonCommonView>);
409 static_assert(!std::ranges::common_range<SizedBidiNonCommonView>);
410 LIBCPP_STATIC_ASSERT(std::ranges::__simple_view<SizedBidiNonCommonView>);
411 
412 using NonSimpleSizedBidiNonCommonView =
413     BasicView<bidirectional_iterator<const int*>, sized_sentinel<bidirectional_iterator<const int*>>,
414               bidirectional_iterator<int*>, sized_sentinel<bidirectional_iterator<int*>>>;
415 static_assert(std::ranges::sized_range<NonSimpleSizedBidiNonCommonView>);
416 static_assert(std::ranges::bidirectional_range<NonSimpleSizedBidiNonCommonView>);
417 static_assert(!std::ranges::random_access_range<NonSimpleSizedBidiNonCommonView>);
418 static_assert(!std::ranges::common_range<NonSimpleSizedBidiNonCommonView>);
419 LIBCPP_STATIC_ASSERT(!std::ranges::__simple_view<NonSimpleSizedBidiNonCommonView>);
420 
421 namespace adltest{
422 struct iter_move_swap_iterator {
423 
424   std::reference_wrapper<int> iter_move_called_times;
425   std::reference_wrapper<int> iter_swap_called_times;
426   int i = 0;
427 
428   using iterator_category = std::input_iterator_tag;
429   using value_type = int;
430   using difference_type = intptr_t;
431 
432   constexpr int operator*() const { return i; }
433 
434   constexpr iter_move_swap_iterator& operator++() {
435     ++i;
436     return *this;
437   }
438   constexpr void operator++(int) { ++i; }
439 
440   friend constexpr bool operator==(const iter_move_swap_iterator& x, std::default_sentinel_t) { return x.i == 5; }
441 
iter_moveiter_move_swap_iterator442   friend constexpr int iter_move(iter_move_swap_iterator const& it) {
443     ++it.iter_move_called_times;
444     return it.i;
445   }
iter_swapiter_move_swap_iterator446   friend constexpr void iter_swap(iter_move_swap_iterator const& x, iter_move_swap_iterator const& y) {
447     ++x.iter_swap_called_times;
448     ++y.iter_swap_called_times;
449   }
450 };
451 
452 struct IterMoveSwapRange {
453   int iter_move_called_times = 0;
454   int iter_swap_called_times = 0;
beginIterMoveSwapRange455   constexpr auto begin() { return iter_move_swap_iterator{iter_move_called_times, iter_swap_called_times}; }
endIterMoveSwapRange456   constexpr auto end() const { return std::default_sentinel; }
457 };
458 } // namespace adltest
459 
460 #endif // TEST_STD_RANGES_RANGE_ADAPTORS_RANGE_ZIP_TYPES_H
461