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// UNSUPPORTED: c++03, c++11, c++14, c++17
10
11// template<indirectly_readable T>
12// using indirect-value-t = see below; // exposition only
13
14#include <cassert>
15
16#include <algorithm>
17#include <memory>
18#include <ranges>
19#include <utility>
20#include <vector>
21
22#include "test_macros.h"
23
24TEST_CONSTEXPR_CXX23 void test() {
25 auto ints = std::views::iota(0, 5);
26 auto unique_ptr_maker = []<std::movable T>(T v) { return std::make_unique<T>(std::move(v)); };
27
28 using iota_iter = std::ranges::iterator_t<decltype(ints)>;
29 using unique_ptr_projection = decltype(unique_ptr_maker);
30 using projected_iter = std::projected<iota_iter, unique_ptr_projection>;
31
32 { // Check std::indirectly_unary_invocable
33 auto consume = [](auto) {};
34 static_assert(std::indirectly_unary_invocable<decltype(consume), projected_iter>);
35
36 std::ranges::for_each(ints, consume, unique_ptr_maker);
37 std::ranges::for_each(ints.begin(), ints.end(), consume, unique_ptr_maker);
38 }
39
40 { // Check std::indirectly_regular_unary_invocable
41 static_assert(std::indirectly_regular_unary_invocable<decltype([](auto) {}), projected_iter>);
42 using check_wellformedness [[maybe_unused]] = std::projected<projected_iter, unique_ptr_projection>;
43 }
44
45 { // Check std::indirect_unary_predicate
46 auto unary_pred = [](auto) { return false; };
47 static_assert(std::indirect_unary_predicate<decltype(unary_pred), projected_iter>);
48
49 assert(std::ranges::find_if(ints, unary_pred, unique_ptr_maker) == ints.end());
50 assert(std::ranges::find_if(ints.begin(), ints.end(), unary_pred, unique_ptr_maker) == ints.end());
51 assert(std::ranges::count_if(ints, unary_pred, unique_ptr_maker) == 0);
52 assert(std::ranges::count_if(ints.begin(), ints.end(), unary_pred, unique_ptr_maker) == 0);
53 }
54
55 { // Check std::indirect_binary_predicate
56 auto binary_pred = [](auto, auto) { return false; };
57 static_assert(std::indirect_binary_predicate<decltype(binary_pred), projected_iter, projected_iter>);
58
59 assert(std::ranges::adjacent_find(ints, binary_pred, unique_ptr_maker) == ints.end());
60 assert(std::ranges::adjacent_find(ints.begin(), ints.end(), binary_pred, unique_ptr_maker) == ints.end());
61 }
62
63 { // Check std::indirect_equivalence_relation
64 auto rel = [](auto, auto) { return false; };
65 static_assert(std::indirect_equivalence_relation<decltype(rel), projected_iter>);
66
67 std::vector<int> out;
68 (void)std::ranges::unique_copy(ints, std::back_inserter(out), rel, unique_ptr_maker);
69 (void)std::ranges::unique_copy(ints.begin(), ints.end(), std::back_inserter(out), rel, unique_ptr_maker);
70 }
71
72 { // Check std::indirect_strict_weak_order
73 auto rel = [](auto x, auto y) { return *x < *y; };
74 static_assert(std::indirect_strict_weak_order<decltype(rel), projected_iter>);
75
76 assert(std::ranges::is_sorted_until(ints, rel, unique_ptr_maker) == ints.end());
77 assert(std::ranges::is_sorted_until(ints.begin(), ints.end(), rel, unique_ptr_maker) == ints.end());
78 }
79}
80
81int main(int, char**) {
82 test();
83#if TEST_STD_VER >= 23
84 static_assert((test(), true));
85#endif
86 return 0;
87}
88

source code of libcxx/test/std/iterators/iterator.requirements/indirectcallable.traits/indirect.value.t.pass.cpp