-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathtri_list_example.cc
108 lines (80 loc) · 2.84 KB
/
tri_list_example.cc
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
#include <vector>
#include <variant>
#include <concepts>
#include <iostream>
#include <numbers>
#include <string>
#include <cassert>
#include <algorithm>
#include <ranges>
#include <limits>
#include <iterator>
#include "tri_list.h"
#include "tri_list_concepts.h"
int main() {
static_assert(is_tri_list_valid<tri_list<int, float, bool>, int, float, bool>);
static_assert(modifier<decltype(identity<int>), int>);
tri_list<int, float, bool> l({1, 2, true, 4.f});
l.modify_only<int>([] (int x) {return x * 2;});
l.modify_only<int, decltype([] (int x) {return x + 2;})>();
std::vector<int> ints;
for (auto it = l.begin(); it != l.end(); ++it) {
std::visit([&]<typename T> (T t) -> void {
if constexpr (std::same_as<T, int>) {
ints.push_back(t);
}
return;
}, *it);
}
assert((std::vector{ints} == std::vector{4, 6}));
for (auto i : l.range_over<float>()) {
std::cout << i - std::numbers::pi_v<float> << '\n';
}
using namespace std::string_literals;
tri_list<int, std::string, std::vector<std::string>> l2 = {
1, 2, "This", 21, "is",
std::vector{"This"s, "is"s, "a"s, "vector"s},
"a", 3, "string", 720
};
std::ranges::copy(l2.range_over<std::string>(), std::ostream_iterator<std::string>(std::cout, ", "));
std::cout << '\n';
auto bad_iter = std::ranges::max_element(l.range_over<int>());
static_assert(std::same_as<decltype(bad_iter), std::ranges::dangling>);
using V = std::variant<int, std::string, std::vector<std::string>>;
auto good_iter = std::ranges::max_element(l2, std::ranges::less{}, [](const V& v) -> int {
if (std::holds_alternative<int>(v)) {
return std::get<int>(v);
} else {
return std::numeric_limits<int>::min();
}
});
assert((std::get<int>(*good_iter) == 720));
tri_list<int, float, bool> l3 = {true, 4.f, true, 5.f, true, 1, 1, 1};
l3.modify_only<bool>([]([[maybe_unused]] bool b) {
return false;
});
std::cout << std::ranges::count(l3.range_over<int>(), 1) << '\n';
float acc = 0;
for (const auto& var: l3) {
if (std::holds_alternative<float>(var)) {
acc += std::get<float>(var);
}
if (std::holds_alternative<int>(var)) {
acc += std::get<int>(var);
}
}
std::cout << acc << '\n';
tri_list<char, bool, int> l4 = {true};
for (int i = 0; i < 2000; ++i) {
auto f = compose<int>(
[](int c) {return c + 1;},
identity<int>);
l4.modify_only<int>(f);
}
l4.push_back(0);
assert(std::get<int>(*++std::begin(l4)) == 2000);
l4.reset<int>();
assert(std::get<int>(*++std::begin(l4)) == 0);
auto view_copy = l4.range_over<int>();
assert(*std::ranges::begin(view_copy) == 0);
}