idol
A C++ Framework for Optimization
Loading...
Searching...
No Matches
Vector.h
1//
2// Created by henri on 16/10/22.
3//
4
5#ifndef IDOL_VECTOR_H
6#define IDOL_VECTOR_H
7
8#include <array>
9#include <vector>
10#include <functional>
11
12namespace idol {
13 template<unsigned int N>
14 class Dim;
15}
16
17template<unsigned int N>
18class idol::Dim : public std::array<unsigned int, N> {
19 friend class Dim<N+1>;
20public:
21 explicit Dim(std::array<unsigned int, N> t_dims) : std::array<unsigned int, N>(std::move(t_dims)) {}
22 template<class ...ArgsT> explicit Dim(ArgsT&& ...t_args) : std::array<unsigned int, N>({ (unsigned int) t_args... }) {
23 static_assert(sizeof...(ArgsT) == N);
24 }
25};
26
27namespace idol::impl {
28
29 template<class T, unsigned int N>
30 struct Vector {
31 using type = std::vector<typename Vector<T, N - 1>::type>;
32 };
33
34 template<class T>
35 struct Vector<T, 0> {
36 using type = T;
37 };
38
39}
40
41namespace idol {
42 template<class T, unsigned int N = 1> using Vector = typename impl::Vector<T, N>::type;
43
44
45 template<class T, unsigned int Size>
46 unsigned int n_entries(const Vector<T, Size> &t_vector) {
47
48 if constexpr (Size == 1) {
49
50 return t_vector.size();
51
52 } else {
53
54 unsigned int result = 0;
55 for (const auto &vec: t_vector) {
56 result += n_entries<T, Size - 1>(vec);
57 }
58
59 return result;
60 }
61
62 }
63
64 template<class T, unsigned int Size>
65 void append(std::vector<T> &t_dest, const Vector<T, Size> &t_vector) {
66 if constexpr (Size == 1) {
67
68 for (const T &elem: t_vector) {
69 t_dest.emplace_back(elem);
70 }
71
72 } else {
73
74 for (const auto &vec: t_vector) {
75 append(t_dest, vec);
76 }
77
78 }
79 }
80
81 template<class T, unsigned int Size>
82 std::vector<T> flatten(const Vector<T, Size> &t_vector) {
83
84 if constexpr (Size == 1) {
85
86 return t_vector;
87
88 } else {
89
90 std::vector<T> result;
91 result.reserve(n_entries<T, Size>(t_vector));
92
93 for (const auto &vec: t_vector) {
94 append<T, Size - 1>(result, vec);
95 }
96
97 return result;
98 }
99 }
100
101 template<class T, unsigned int Size>
102 void apply(Vector<T, Size> &t_vec, const std::function<void(T &)> &t_function) {
103
104 if constexpr (Size == 1) {
105
106 for (auto &elem: t_vec) {
107 t_function(elem);
108 }
109
110 } else {
111
112 for (auto &elem: t_vec) {
113 apply<T, Size - 1>(elem, t_function);
114 }
115
116 }
117
118 }
119
120
121 template<class T, unsigned int Size>
122 void apply(const Vector<T, Size> &t_vec, const std::function<void(const T &)> &t_function) {
123
124 if constexpr (Size == 1) {
125
126 for (const auto &elem: t_vec) {
127 t_function(elem);
128 }
129
130 } else {
131
132 for (const auto &elem: t_vec) {
133 apply<T, Size - 1>(elem, t_function);
134 }
135
136 }
137
138 }
139
140 template<class T, class U, unsigned int Size>
141 Vector<U, Size> transform(const Vector<T, Size> &t_vec, const std::function<U(const T &)> &t_function) {
142
143 Vector<U, Size> result;
144 result.reserve(t_vec.size());
145
146 if constexpr (Size == 1) {
147
148 for (const auto &elem: t_vec) {
149 result.emplace_back(t_function(elem));
150 }
151
152 } else {
153
154 for (const auto &elem: t_vec) {
155 result.emplace_back(transform<T, U, Size - 1>(elem, t_function));
156 }
157
158 }
159
160 return result;
161
162 }
163}
164
165#endif //IDOL_VECTOR_H