1 // Copyright (C) 2020-2025 Free Software Foundation, Inc.
3 // This file is part of the GNU ISO C++ Library. This library is free
4 // software; you can redistribute it and/or modify it under the
5 // terms of the GNU General Public License as published by the
6 // Free Software Foundation; either version 3, or (at your option)
9 // This library is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU General Public License for more details.
14 // You should have received a copy of the GNU General Public License along
15 // with this library; see the file COPYING3. If not see
16 // <http://www.gnu.org/licenses/>.
18 // { dg-do run { target c++20 } }
22 #include <testsuite_hooks.h>
23 #include <testsuite_iterators.h>
25 using __gnu_test::test_container
;
26 using __gnu_test::test_range
;
27 using __gnu_test::bidirectional_iterator_wrapper
;
29 namespace ranges
= std::ranges
;
36 constexpr X() : i(0) { }
37 constexpr X(int a
) : i(a
) { }
39 constexpr X(const X
&) = delete;
40 constexpr X
& operator=(const X
&) = delete;
42 constexpr X(X
&& other
)
44 *this = std::move(other
);
56 operator==(const X
& a
, const X
& b
)
57 { return a
.i
== b
.i
; }
64 X x
[7] = { 1, 2, 3, 4, 5, 6, 7 };
65 X y
[7] = { 0, 0, 0, 0, 0, 0, 0 };
66 X z
[7] = { 1, 2, 3, 4, 5, 6, 7 };
67 auto [in
, out
] = ranges::move_backward(x
, y
+7);
68 VERIFY( ranges::equal(x
, y
) && in
== x
+7 && out
== y
);
69 VERIFY( ranges::equal(x
, z
) );
73 int x
[3] = { 1, 2, 3 };
75 int z
[3] = { 1, 2, 3 };
76 test_container
<int, bidirectional_iterator_wrapper
> cx(x
);
77 test_container
<char, bidirectional_iterator_wrapper
> cy(y
);
78 auto [in
, out
] = ranges::move_backward(cx
, cy
.end());
79 VERIFY( ranges::equal(x
, x
+3, y
+1, y
+4) && in
.ptr
== x
+3 && out
.ptr
== y
+1 );
80 VERIFY( ranges::equal(x
, z
) );
84 std::vector
<char> x
= {1,2,3};
85 std::vector
<int> y(3);
86 const int z
[3] = { 1, 2, 3 };
87 auto [in
, out
] = ranges::move_backward(x
, ranges::end(y
));
88 VERIFY( in
== x
.begin()+3 );
89 VERIFY( out
== y
.begin() );
90 VERIFY( ranges::equal(y
, z
) && ranges::equal(x
, z
) );
95 std::vector
<int> x
= {1,2,3};
96 std::vector
<int> y(3);
97 const int z
[3] = { 1, 2, 3 };
98 auto [in
, out
] = ranges::move_backward(x
, ranges::end(y
));
99 VERIFY( in
== x
.begin()+3 );
100 VERIFY( out
== y
.begin() );
101 VERIFY( ranges::equal(y
, z
) && ranges::equal(x
, z
) );
105 std::vector
<int> x
= {1,2,3};
106 std::vector
<int> y(3);
107 const int z
[3] = { 1, 2, 3 };
108 auto [in
,out
] = ranges::move_backward(make_reverse_iterator(x
.end()),
109 make_reverse_iterator(x
.begin()),
110 make_reverse_iterator(y
.begin()));
111 VERIFY( in
.base() == x
.begin()+3 );
112 VERIFY( out
.base() == y
.begin()+3 );
113 VERIFY( ranges::equal(y
, z
) && ranges::equal(x
, z
) );
117 std::vector
<char> x
= {1,2,3};
118 std::vector
<int> y(3);
119 const int z
[3] = { 1, 2, 3 };
120 auto [in
,out
] = ranges::move_backward(make_reverse_iterator(x
.end()),
121 make_reverse_iterator(x
.begin()),
122 make_reverse_iterator(y
.begin()));
123 VERIFY( in
.base() == x
.begin()+3 );
124 VERIFY( out
.base() == y
.begin()+3 );
125 VERIFY( ranges::equal(y
, z
) && ranges::equal(x
, z
) );
132 X x
[] = { {2}, {2}, {6}, {8}, {10} };
133 X y
[] = { {2}, {6}, {8}, {10}, {11}, {2} };
134 const X z
[] = { {2}, {2}, {6}, {8}, {10} };
135 auto [in
, out
] = ranges::move_backward(x
, ranges::end(y
));
136 VERIFY( ranges::equal(x
, x
+5, y
+1, y
+6) );
138 VERIFY( out
== y
+1 );
139 VERIFY( y
[0].i
== 2 );
140 VERIFY( ranges::equal(x
, z
) );
141 VERIFY( ranges::count(x
, 1, &X::moved
) == 5 );
142 VERIFY( ranges::count(y
, 0, &X::moved
) == 6 );
149 X x
[] = { {2}, {2}, {6}, {8}, {10} };
150 X y
[] = { {2}, {6}, {8}, {10}, {11}, {2} };
151 const X z
[] = { {2}, {2}, {6}, {8}, {10} };
152 auto [in
, out
] = ranges::move_backward(x
, ranges::end(y
));
153 ok
&= ranges::equal(x
, x
+5, y
+1, y
+6);
157 ok
&= ranges::equal(x
, z
);
158 ok
&= ranges::count(x
, 1, &X::moved
) == 5;
159 ok
&= ranges::count(y
, 0, &X::moved
) == 6;
168 static_assert(test03());