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 // <algorithm>
10 
11 // template<InputIterator InIter, OutputIterator<auto, InIter::reference> OutIter>
12 //   constexpr OutIter   // constexpr after C++17
13 //   copy_n(InIter first, InIter::difference_type n, OutIter result);
14 
15 #include <algorithm>
16 #include <cassert>
17 
18 #include "test_macros.h"
19 #include "test_iterators.h"
20 #include "user_defined_integral.h"
21 
22 typedef UserDefinedIntegral<unsigned> UDI;
23 
24 template <class InIter, class OutIter>
25 TEST_CONSTEXPR_CXX20 void
test_copy_n()26 test_copy_n()
27 {
28     const unsigned N = 1000;
29     int ia[N] = {};
30     for (unsigned i = 0; i < N; ++i)
31         ia[i] = i;
32     int ib[N] = {0};
33 
34     OutIter r = std::copy_n(InIter(ia), UDI(N/2), OutIter(ib));
35     assert(base(r) == ib+N/2);
36     for (unsigned i = 0; i < N/2; ++i)
37         assert(ia[i] == ib[i]);
38 }
39 
40 TEST_CONSTEXPR_CXX20 bool
test()41 test()
42 {
43     test_copy_n<input_iterator<const int*>, output_iterator<int*> >();
44     test_copy_n<input_iterator<const int*>, input_iterator<int*> >();
45     test_copy_n<input_iterator<const int*>, forward_iterator<int*> >();
46     test_copy_n<input_iterator<const int*>, bidirectional_iterator<int*> >();
47     test_copy_n<input_iterator<const int*>, random_access_iterator<int*> >();
48     test_copy_n<input_iterator<const int*>, int*>();
49 
50     test_copy_n<forward_iterator<const int*>, output_iterator<int*> >();
51     test_copy_n<forward_iterator<const int*>, input_iterator<int*> >();
52     test_copy_n<forward_iterator<const int*>, forward_iterator<int*> >();
53     test_copy_n<forward_iterator<const int*>, bidirectional_iterator<int*> >();
54     test_copy_n<forward_iterator<const int*>, random_access_iterator<int*> >();
55     test_copy_n<forward_iterator<const int*>, int*>();
56 
57     test_copy_n<bidirectional_iterator<const int*>, output_iterator<int*> >();
58     test_copy_n<bidirectional_iterator<const int*>, input_iterator<int*> >();
59     test_copy_n<bidirectional_iterator<const int*>, forward_iterator<int*> >();
60     test_copy_n<bidirectional_iterator<const int*>, bidirectional_iterator<int*> >();
61     test_copy_n<bidirectional_iterator<const int*>, random_access_iterator<int*> >();
62     test_copy_n<bidirectional_iterator<const int*>, int*>();
63 
64     test_copy_n<random_access_iterator<const int*>, output_iterator<int*> >();
65     test_copy_n<random_access_iterator<const int*>, input_iterator<int*> >();
66     test_copy_n<random_access_iterator<const int*>, forward_iterator<int*> >();
67     test_copy_n<random_access_iterator<const int*>, bidirectional_iterator<int*> >();
68     test_copy_n<random_access_iterator<const int*>, random_access_iterator<int*> >();
69     test_copy_n<random_access_iterator<const int*>, int*>();
70 
71     test_copy_n<const int*, output_iterator<int*> >();
72     test_copy_n<const int*, input_iterator<int*> >();
73     test_copy_n<const int*, forward_iterator<int*> >();
74     test_copy_n<const int*, bidirectional_iterator<int*> >();
75     test_copy_n<const int*, random_access_iterator<int*> >();
76     test_copy_n<const int*, int*>();
77 
78   return true;
79 }
80 
main(int,char **)81 int main(int, char**)
82 {
83     test();
84 
85 #if TEST_STD_VER > 17 && !defined(_LIBCPP_HAS_NO_BUILTIN_IS_CONSTANT_EVALUATED)
86     static_assert(test());
87 #endif
88 
89   return 0;
90 }
91