move_backward.cpp 6.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217
  1. // Range v3 library
  2. //
  3. // Copyright Eric Niebler 2014-present
  4. //
  5. // Use, modification and distribution is subject to the
  6. // Boost Software License, Version 1.0. (See accompanying
  7. // file LICENSE_1_0.txt or copy at
  8. // http://www.boost.org/LICENSE_1_0.txt)
  9. //
  10. // Project home: https://github.com/ericniebler/range-v3
  11. //===----------------------------------------------------------------------===//
  12. //
  13. // The LLVM Compiler Infrastructure
  14. //
  15. // This file is dual licensed under the MIT and the University of Illinois Open
  16. // Source Licenses. See LICENSE.TXT for details.
  17. //
  18. //===----------------------------------------------------------------------===//
  19. #include <memory>
  20. #include <algorithm>
  21. #include <range/v3/core.hpp>
  22. #include <range/v3/algorithm/move_backward.hpp>
  23. #include "../simple_test.hpp"
  24. #include "../test_utils.hpp"
  25. #include "../test_iterators.hpp"
  26. template<typename InIter, typename OutIter>
  27. void
  28. test()
  29. {
  30. {
  31. const int N = 1000;
  32. int ia[N];
  33. for(int i = 0; i < N; ++i)
  34. ia[i] = i;
  35. int ib[N] = {0};
  36. ranges::move_backward_result<InIter, OutIter> r =
  37. ranges::move_backward(InIter(ia), InIter(ia+N), OutIter(ib+N));
  38. CHECK(base(r.in) == ia+N);
  39. CHECK(base(r.out) == ib);
  40. for(int i = 0; i < N; ++i)
  41. CHECK(ia[i] == ib[i]);
  42. }
  43. {
  44. const int N = 1000;
  45. int ia[N];
  46. for(int i = 0; i < N; ++i)
  47. ia[i] = i;
  48. int ib[N] = {0};
  49. ranges::move_backward_result<InIter, OutIter> r =
  50. ranges::move_backward(ranges::make_subrange(InIter(ia), InIter(ia+N)), OutIter(ib+N));
  51. CHECK(base(r.in) == ia+N);
  52. CHECK(base(r.out) == ib);
  53. for(int i = 0; i < N; ++i)
  54. CHECK(ia[i] == ib[i]);
  55. }
  56. }
  57. template<typename InIter, typename OutIter, typename Sent = InIter>
  58. constexpr bool test_constexpr()
  59. {
  60. {
  61. constexpr int N = 1000;
  62. int ia[N]{1};
  63. for(int i = 0; i < N; ++i)
  64. ia[i] = i;
  65. int ib[N] = {0};
  66. const auto r = ranges::move_backward(InIter(ia), Sent(ia + N), OutIter(ib + N));
  67. if(base(r.in) != ia + N)
  68. {
  69. return false;
  70. }
  71. if(base(r.out) != ib)
  72. {
  73. return false;
  74. }
  75. for(int i = 0; i < N; ++i)
  76. if(ia[i] != ib[i])
  77. {
  78. return false;
  79. }
  80. }
  81. {
  82. constexpr int N = 1000;
  83. int ia[N]{1};
  84. for(int i = 0; i < N; ++i)
  85. ia[i] = i;
  86. int ib[N] = {0};
  87. const auto r = ranges::move_backward(
  88. as_lvalue(ranges::make_subrange(InIter(ia), Sent(ia + N))), OutIter(ib + N));
  89. if(base(r.in) != ia + N)
  90. {
  91. return false;
  92. }
  93. if(base(r.out) != ib)
  94. {
  95. return false;
  96. }
  97. for(int i = 0; i < N; ++i)
  98. if(ia[i] != ib[i])
  99. {
  100. return false;
  101. }
  102. }
  103. return true;
  104. }
  105. struct S
  106. {
  107. std::unique_ptr<int> p;
  108. };
  109. template<typename InIter, typename OutIter>
  110. void
  111. test1()
  112. {
  113. {
  114. const int N = 100;
  115. std::unique_ptr<int> ia[N];
  116. for(int i = 0; i < N; ++i)
  117. ia[i].reset(new int(i));
  118. std::unique_ptr<int> ib[N];
  119. ranges::move_backward_result<InIter, OutIter> r =
  120. ranges::move_backward(InIter(ia), InIter(ia+N), OutIter(ib+N));
  121. CHECK(base(r.in) == ia+N);
  122. CHECK(base(r.out) == ib);
  123. for(int i = 0; i < N; ++i)
  124. {
  125. CHECK(ia[i].get() == nullptr);
  126. CHECK(*ib[i] == i);
  127. }
  128. }
  129. {
  130. const int N = 100;
  131. std::unique_ptr<int> ia[N];
  132. for(int i = 0; i < N; ++i)
  133. ia[i].reset(new int(i));
  134. std::unique_ptr<int> ib[N];
  135. ranges::move_backward_result<InIter, OutIter> r =
  136. ranges::move_backward(ranges::make_subrange(InIter(ia), InIter(ia+N)), OutIter(ib+N));
  137. CHECK(base(r.in) == ia+N);
  138. CHECK(base(r.out) == ib);
  139. for(int i = 0; i < N; ++i)
  140. {
  141. CHECK(ia[i].get() == nullptr);
  142. CHECK(*ib[i] == i);
  143. }
  144. ranges::move_backward(ib, ib+N, ia+N);
  145. auto r2 = ranges::move_backward(ranges::make_subrange(InIter(ia), InIter(ia+N)), OutIter(ib+N));
  146. CHECK(base(r2.in) == ia+N);
  147. CHECK(base(r2.out) == ib);
  148. for(int i = 0; i < N; ++i)
  149. {
  150. CHECK(ia[i].get() == nullptr);
  151. CHECK(*ib[i] == i);
  152. }
  153. }
  154. }
  155. int main()
  156. {
  157. test<BidirectionalIterator<const int*>, BidirectionalIterator<int*> >();
  158. test<BidirectionalIterator<const int*>, RandomAccessIterator<int*> >();
  159. test<BidirectionalIterator<const int*>, int*>();
  160. test<RandomAccessIterator<const int*>, BidirectionalIterator<int*> >();
  161. test<RandomAccessIterator<const int*>, RandomAccessIterator<int*> >();
  162. test<RandomAccessIterator<const int*>, int*>();
  163. test<const int*, BidirectionalIterator<int*> >();
  164. test<const int*, RandomAccessIterator<int*> >();
  165. test<const int*, int*>();
  166. test1<BidirectionalIterator<std::unique_ptr<int>*>, BidirectionalIterator<std::unique_ptr<int>*> >();
  167. test1<BidirectionalIterator<std::unique_ptr<int>*>, RandomAccessIterator<std::unique_ptr<int>*> >();
  168. test1<BidirectionalIterator<std::unique_ptr<int>*>, std::unique_ptr<int>*>();
  169. test1<RandomAccessIterator<std::unique_ptr<int>*>, BidirectionalIterator<std::unique_ptr<int>*> >();
  170. test1<RandomAccessIterator<std::unique_ptr<int>*>, RandomAccessIterator<std::unique_ptr<int>*> >();
  171. test1<RandomAccessIterator<std::unique_ptr<int>*>, std::unique_ptr<int>*>();
  172. test1<std::unique_ptr<int>*, BidirectionalIterator<std::unique_ptr<int>*> >();
  173. test1<std::unique_ptr<int>*, RandomAccessIterator<std::unique_ptr<int>*> >();
  174. test1<std::unique_ptr<int>*, std::unique_ptr<int>*>();
  175. STATIC_CHECK(test_constexpr<BidirectionalIterator<const int *>,
  176. BidirectionalIterator<int *>>());
  177. STATIC_CHECK(test_constexpr<BidirectionalIterator<const int *>,
  178. RandomAccessIterator<int *>>());
  179. STATIC_CHECK(test_constexpr<BidirectionalIterator<const int *>, int *>());
  180. STATIC_CHECK(test_constexpr<RandomAccessIterator<const int *>,
  181. BidirectionalIterator<int *>>());
  182. STATIC_CHECK(
  183. test_constexpr<RandomAccessIterator<const int *>, RandomAccessIterator<int *>>());
  184. STATIC_CHECK(test_constexpr<RandomAccessIterator<const int *>, int *>());
  185. STATIC_CHECK(test_constexpr<const int *, BidirectionalIterator<int *>>());
  186. STATIC_CHECK(test_constexpr<const int *, RandomAccessIterator<int *>>());
  187. STATIC_CHECK(test_constexpr<const int *, int *>());
  188. return test_result();
  189. }