1 // -*- C++ -*-
2 // { dg-options "-ltbb" }
3 // { dg-do run { target c++17 } }
4 // { dg-timeout-factor 3 }
5 // { dg-require-effective-target tbb-backend }
6
7 //===-- adjacent_find.pass.cpp --------------------------------------------===//
8 //
9 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
10 // See https://llvm.org/LICENSE.txt for license information.
11 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
12 //
13 //===----------------------------------------------------------------------===//
14
15 #include "pstl/pstl_test_config.h"
16
17 #ifdef PSTL_STANDALONE_TESTS
18
19 #include "pstl/execution"
20 #include "pstl/algorithm"
21 #else
22 #include <execution>
23 #include <algorithm>
24 #endif // PSTL_STANDALONE_TESTS
25
26 #include "pstl/test_utils.h"
27
28 using namespace TestUtils;
29
30 struct test_adjacent_find
31 {
32 template <typename Policy, typename Iterator, typename Pred>
33 void
operator ()test_adjacent_find34 operator()(Policy&& exec, Iterator first, Iterator last, Pred pred)
35 {
36 using namespace std;
37
38 auto k = std::adjacent_find(first, last, pred);
39 auto i = adjacent_find(exec, first, last, pred);
40 EXPECT_TRUE(i == k, "wrong return value from adjacent_find with predicate");
41
42 i = adjacent_find(exec, first, last);
43 EXPECT_TRUE(i == k, "wrong return value from adjacent_find without predicate");
44 }
45 };
46
47 template <typename T>
48 void
test_adjacent_find_by_type()49 test_adjacent_find_by_type()
50 {
51
52 size_t counts[] = {2, 3, 500};
53 for (int32_t c = 0; c < const_size(counts); ++c)
54 {
55
56 for (int32_t e = 0; e < (counts[c] >= 64 ? 64 : (counts[c] == 2 ? 1 : 2)); ++e)
57 {
58 Sequence<T> in(counts[c], [](int32_t v) -> T { return T(v); }); //fill 0...n
59 in[e] = in[e + 1] = -1; //make an adjacent pair
60
61 auto i = std::adjacent_find(in.cbegin(), in.cend(), std::equal_to<T>());
62 EXPECT_TRUE(i == in.cbegin() + e, "std::adjacent_find returned wrong result");
63
64 invoke_on_all_policies(test_adjacent_find(), in.begin(), in.end(), std::equal_to<T>());
65 invoke_on_all_policies(test_adjacent_find(), in.cbegin(), in.cend(), std::equal_to<T>());
66 }
67 }
68
69 //special cases: size=0, size=1;
70 for (int32_t expect = 0; expect < 1; ++expect)
71 {
72 Sequence<T> in(expect, [](int32_t v) -> T { return T(v); }); //fill 0...n
73 auto i = std::adjacent_find(in.cbegin(), in.cend(), std::equal_to<T>());
74 EXPECT_TRUE(i == in.cbegin() + expect, "std::adjacent_find returned wrong result");
75
76 invoke_on_all_policies(test_adjacent_find(), in.begin(), in.end(), std::equal_to<T>());
77 invoke_on_all_policies(test_adjacent_find(), in.cbegin(), in.cend(), std::equal_to<T>());
78 }
79
80 //special cases:
81 Sequence<T> a1 = {5, 5, 5, 6, 7, 8, 9};
82 invoke_on_all_policies(test_adjacent_find(), a1.begin(), a1.end(), std::equal_to<T>());
83 invoke_on_all_policies(test_adjacent_find(), a1.begin() + 1, a1.end(), std::equal_to<T>());
84
85 invoke_on_all_policies(test_adjacent_find(), a1.cbegin(), a1.cend(), std::equal_to<T>());
86 invoke_on_all_policies(test_adjacent_find(), a1.cbegin() + 1, a1.cend(), std::equal_to<T>());
87
88 Sequence<T> a2 = {5, 6, 7, 8, 9, 9};
89 invoke_on_all_policies(test_adjacent_find(), a2.begin(), a2.end(), std::equal_to<T>());
90 invoke_on_all_policies(test_adjacent_find(), a2.begin(), a2.end() - 1, std::equal_to<T>());
91
92 invoke_on_all_policies(test_adjacent_find(), a2.cbegin(), a2.cend(), std::equal_to<T>());
93 invoke_on_all_policies(test_adjacent_find(), a2.cbegin(), a2.cend() - 1, std::equal_to<T>());
94
95 Sequence<T> a3 = {5, 6, 6, 6, 7, 9, 9, 9, 9};
96 invoke_on_all_policies(test_adjacent_find(), a3.begin(), a3.end(), std::equal_to<T>());
97
98 invoke_on_all_policies(test_adjacent_find(), a3.cbegin(), a3.cend(), std::equal_to<T>());
99 }
100
101 template <typename T>
102 struct test_non_const
103 {
104 template <typename Policy, typename Iterator>
105 void
operator ()test_non_const106 operator()(Policy&& exec, Iterator iter)
107 {
108 adjacent_find(exec, iter, iter, non_const(std::equal_to<T>()));
109 }
110 };
111
112 int32_t
main()113 main()
114 {
115
116 test_adjacent_find_by_type<int32_t>();
117 test_adjacent_find_by_type<float64_t>();
118
119 test_algo_basic_single<int32_t>(run_for_rnd_bi<test_non_const<int32_t>>());
120
121 std::cout << done() << std::endl;
122 return 0;
123 }
124