1//===----------------------------------------------------------------------===//
2//
3//                     The LLVM Compiler Infrastructure
4//
5// This file is dual licensed under the MIT and the University of Illinois Open
6// Source Licenses. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10// <algorithm>
11
12// template<InputIterator InIter, OutputIterator<auto, InIter::reference> OutIter,
13//          Predicate<auto, InIter::value_type> Pred>
14//   requires CopyConstructible<Pred>
15//   OutIter
16//   copy_if(InIter first, InIter last, OutIter result, Pred pred);
17
18#include <algorithm>
19#include <cassert>
20
21#include "test_iterators.h"
22
23struct Pred
24{
25    bool operator()(int i) {return i % 3 == 0;}
26};
27
28template <class InIter, class OutIter>
29void
30test()
31{
32    const unsigned N = 1000;
33    int ia[N];
34    for (unsigned i = 0; i < N; ++i)
35        ia[i] = i;
36    int ib[N] = {0};
37
38    OutIter r = std::copy_if(InIter(ia), InIter(ia+N), OutIter(ib), Pred());
39    assert(base(r) == ib+N/3+1);
40    for (unsigned i = 0; i < N/3+1; ++i)
41        assert(ib[i] % 3 == 0);
42}
43
44int main()
45{
46    test<input_iterator<const int*>, output_iterator<int*> >();
47    test<input_iterator<const int*>, input_iterator<int*> >();
48    test<input_iterator<const int*>, forward_iterator<int*> >();
49    test<input_iterator<const int*>, bidirectional_iterator<int*> >();
50    test<input_iterator<const int*>, random_access_iterator<int*> >();
51    test<input_iterator<const int*>, int*>();
52
53    test<forward_iterator<const int*>, output_iterator<int*> >();
54    test<forward_iterator<const int*>, input_iterator<int*> >();
55    test<forward_iterator<const int*>, forward_iterator<int*> >();
56    test<forward_iterator<const int*>, bidirectional_iterator<int*> >();
57    test<forward_iterator<const int*>, random_access_iterator<int*> >();
58    test<forward_iterator<const int*>, int*>();
59
60    test<bidirectional_iterator<const int*>, output_iterator<int*> >();
61    test<bidirectional_iterator<const int*>, input_iterator<int*> >();
62    test<bidirectional_iterator<const int*>, forward_iterator<int*> >();
63    test<bidirectional_iterator<const int*>, bidirectional_iterator<int*> >();
64    test<bidirectional_iterator<const int*>, random_access_iterator<int*> >();
65    test<bidirectional_iterator<const int*>, int*>();
66
67    test<random_access_iterator<const int*>, output_iterator<int*> >();
68    test<random_access_iterator<const int*>, input_iterator<int*> >();
69    test<random_access_iterator<const int*>, forward_iterator<int*> >();
70    test<random_access_iterator<const int*>, bidirectional_iterator<int*> >();
71    test<random_access_iterator<const int*>, random_access_iterator<int*> >();
72    test<random_access_iterator<const int*>, int*>();
73
74    test<const int*, output_iterator<int*> >();
75    test<const int*, input_iterator<int*> >();
76    test<const int*, forward_iterator<int*> >();
77    test<const int*, bidirectional_iterator<int*> >();
78    test<const int*, random_access_iterator<int*> >();
79    test<const int*, int*>();
80}
81