WaveSimPP 1.0
A C library for solving the wave equation and reconstructing the wave field
All Classes Namespaces Functions Modules Pages
variadic.cpp
1#include "boost/multi_array.hpp"
2#include "boost/array.hpp"
3#include "CustomLibraries/np.hpp"
4#include <cassert>
5#include <iostream>
6
7void test_gradient()
8{
9 // Create a 4D array that is 3 x 4 x 2 x 1
10 typedef boost::multi_array<double, 4>::index index;
11 boost::multi_array<double, 4> A(boost::extents[3][4][2][2]);
12
13 // Assign values to the elements
14 int values = 0;
15 for (index i = 0; i != 3; ++i)
16 for (index j = 0; j != 4; ++j)
17 for (index k = 0; k != 2; ++k)
18 for (index l = 0; l != 2; ++l)
19 A[i][j][k][l] = values++;
20
21 // Verify values
22 int verify = 0;
23 for (index i = 0; i != 3; ++i)
24 for (index j = 0; j != 4; ++j)
25 for (index k = 0; k != 2; ++k)
26 for (index l = 0; l != 2; ++l)
27 assert(A[i][j][k][l] == verify++);
28
29 double dx, dy, dz, dt;
30 dx = 1.0;
31 dy = 1.0;
32 dz = 1.0;
33 dt = 1.0;
34 std::vector<boost::multi_array<double, 4>> my_arrays = np::gradient(A, {dx, dy, dz, dt});
35
36 boost::multi_array<double, 1> x = np::linspace(0, 1, 5);
37 std::vector<boost::multi_array<double, 1>> gradf = np::gradient(x, {1.0});
38 for (int i = 0; i < 5; i++)
39 {
40 std::cout << gradf[0][i] << ",";
41 }
42 std::cout << "\n";
43 // np::print(std::cout, my_arrays[0]);
44}
45
46void test_meshgrid()
47{
48 boost::multi_array<double, 1> x = np::linspace(0, 1, 5);
49 boost::multi_array<double, 1> y = np::linspace(0, 1, 5);
50 boost::multi_array<double, 1> z = np::linspace(0, 1, 5);
51 boost::multi_array<double, 1> t = np::linspace(0, 1, 5);
52 const boost::multi_array<double, 1> axis[4] = {x, y, z, t};
53 std::vector<boost::multi_array<double, 4>> my_arrays = np::meshgrid(axis, false, np::xy);
54 // np::print(std::cout, my_arrays[0]);
55 int nx = 3;
56 int ny = 2;
57 boost::multi_array<double, 1> x2 = np::linspace(0, 1, nx);
58 boost::multi_array<double, 1> y2 = np::linspace(0, 1, ny);
59 const boost::multi_array<double, 1> axis2[2] = {x2, y2};
60 std::vector<boost::multi_array<double, 2>> my_arrays2 = np::meshgrid(axis2, false, np::xy);
61 std::cout << "xv\n";
62 for (int i = 0; i < ny; i++)
63 {
64 for (int j = 0; j < nx; j++)
65 {
66 std::cout << my_arrays2[0][i][j] << " ";
67 }
68 std::cout << "\n";
69 }
70 std::cout << "yv\n";
71 for (int i = 0; i < ny; i++)
72 {
73 for (int j = 0; j < nx; j++)
74 {
75 std::cout << my_arrays2[1][i][j] << " ";
76 }
77 std::cout << "\n";
78 }
79}
80
81void test_complex_operations()
82{
83 int nx = 3;
84 int ny = 2;
85 boost::multi_array<double, 1> x = np::linspace(0, 1, nx);
86 boost::multi_array<double, 1> y = np::linspace(0, 1, ny);
87 const boost::multi_array<double, 1> axis[2] = {x, y};
88 std::vector<boost::multi_array<double, 2>> my_arrays = np::meshgrid(axis, false, np::xy);
89 boost::multi_array<double, 2> A = np::sqrt(my_arrays[0]);
90 std::cout << "sqrt\n";
91 for (int i = 0; i < ny; i++)
92 {
93 for (int j = 0; j < nx; j++)
94 {
95 std::cout << A[i][j] << " ";
96 }
97 std::cout << "\n";
98 }
99 std::cout << "\n";
100 float a = 100.0;
101 float sqa = np::sqrt(a);
102 std::cout << "sqrt of " << a << " is " << sqa << "\n";
103 std::cout << "exp\n";
104 boost::multi_array<double, 2> B = np::exp(my_arrays[0]);
105 for (int i = 0; i < ny; i++)
106 {
107 for (int j = 0; j < nx; j++)
108 {
109 std::cout << B[i][j] << " ";
110 }
111 std::cout << "\n";
112 }
113
114 std::cout << "Power\n";
115 boost::multi_array<double, 1> x2 = np::linspace(1, 3, nx);
116 boost::multi_array<double, 1> y2 = np::linspace(1, 3, ny);
117 const boost::multi_array<double, 1> axis2[2] = {x2, y2};
118 std::vector<boost::multi_array<double, 2>> my_arrays2 = np::meshgrid(axis2, false, np::xy);
119 boost::multi_array<double, 2> C = np::pow(my_arrays2[1], 2.0);
120 for (int i = 0; i < ny; i++)
121 {
122 for (int j = 0; j < nx; j++)
123 {
124 std::cout << C[i][j] << " ";
125 }
126 std::cout << "\n";
127 }
128}
129
130void test_equal()
131{
132 boost::multi_array<double, 1> x = np::linspace(0, 1, 5);
133 boost::multi_array<double, 1> y = np::linspace(0, 1, 5);
134 boost::multi_array<double, 1> z = np::linspace(0, 1, 5);
135 boost::multi_array<double, 1> t = np::linspace(0, 1, 5);
136 const boost::multi_array<double, 1> axis[4] = {x, y, z, t};
137 std::vector<boost::multi_array<double, 4>> my_arrays = np::meshgrid(axis, false, np::xy);
138 boost::multi_array<double, 1> x2 = np::linspace(0, 1, 5);
139 boost::multi_array<double, 1> y2 = np::linspace(0, 1, 5);
140 boost::multi_array<double, 1> z2 = np::linspace(0, 1, 5);
141 boost::multi_array<double, 1> t2 = np::linspace(0, 1, 5);
142 const boost::multi_array<double, 1> axis2[4] = {x2, y2, z2, t2};
143 std::vector<boost::multi_array<double, 4>> my_arrays2 = np::meshgrid(axis2, false, np::xy);
144 std::cout << "equality test:\n";
145 std::cout << (bool)(my_arrays == my_arrays2) << "\n";
146}
147void test_basic_operations()
148{
149 int nx = 3;
150 int ny = 2;
151 boost::multi_array<double, 1> x = np::linspace(0, 1, nx);
152 boost::multi_array<double, 1> y = np::linspace(0, 1, ny);
153 const boost::multi_array<double, 1> axis[2] = {x, y};
154 std::vector<boost::multi_array<double, 2>> my_arrays = np::meshgrid(axis, false, np::xy);
155
156 std::cout << "basic operations:\n";
157
158 std::cout << "addition:\n";
159 boost::multi_array<double, 2> A = my_arrays[0] + my_arrays[1];
160
161 for (int i = 0; i < ny; i++)
162 {
163 for (int j = 0; j < nx; j++)
164 {
165 std::cout << A[i][j] << " ";
166 }
167 std::cout << "\n";
168 }
169
170 std::cout << "multiplication:\n";
171 boost::multi_array<double, 2> B = my_arrays[0] * my_arrays[1];
172
173 for (int i = 0; i < ny; i++)
174 {
175 for (int j = 0; j < nx; j++)
176 {
177 std::cout << B[i][j] << " ";
178 }
179 std::cout << "\n";
180 }
181 double coeff = 3;
182 boost::multi_array<double, 1> t = np::linspace(0, 1, nx);
183 boost::multi_array<double, 1> t_time_3 = coeff * t;
184 boost::multi_array<double, 1> t_time_2 = 2.0 * t;
185 std::cout << "t_time_3: ";
186 for (int j = 0; j < nx; j++)
187 {
188 std::cout << t_time_3[j] << " ";
189 }
190 std::cout << "\n";
191 std::cout << "t_time_2: ";
192 for (int j = 0; j < nx; j++)
193 {
194 std::cout << t_time_2[j] << " ";
195 }
196 std::cout << "\n";
197}
198
199void test_zeros()
200{
201 int nx = 3;
202 int ny = 2;
203 int dimensions[] = {ny, nx};
204 boost::multi_array<double, 2> A = np::zeros<double>(dimensions);
205 std::cout << "zeros:\n";
206 for (int i = 0; i < ny; i++)
207 {
208 for (int j = 0; j < nx; j++)
209 {
210 std::cout << A[i][j] << " ";
211 }
212 std::cout << "\n";
213 }
214}
215
216void test_min_max()
217{
218 int nx = 24;
219 int ny = 5;
220 boost::multi_array<double, 1> x = np::linspace(0, 10, nx);
221 boost::multi_array<double, 1> y = np::linspace(-1, 1, ny);
222 const boost::multi_array<double, 1> axis[2] = {x, y};
223 std::vector<boost::multi_array<double, 2>> my_array = np::meshgrid(axis, false, np::xy);
224 std::cout << "min: " << np::min(my_array[0]) << "\n";
225 std::cout << "max: " << np::max(my_array[1]) << "\n";
226 std::cout << "max simple: " << np::max(1.0, 2.0, 3.0, 4.0, 5.0) << "\n";
227 std::cout << "min simple: " << np::min(1, -2, 3, -4, 5) << "\n";
228}
229
230void test_toy_problem()
231{
232 boost::multi_array<double, 1> x = np::linspace(0, 1, 100);
233 boost::multi_array<double, 1> y = np::linspace(0, 1, 100);
234 // x = np::pow(x, 2.0);
235 // y = np::pow(y, 3.0);
236
237 const boost::multi_array<double, 1> axis[2] = {x, y};
238 std::vector<boost::multi_array<double, 2>> XcY = np::meshgrid(axis, false, np::xy);
239
240 double dx, dy;
241 dx = 1.0 / 100.0;
242 dy = 1.0 / 100.0;
243
244 boost::multi_array<double, 2> f = np::pow(XcY[0], 2.0) + XcY[0] * np::pow(XcY[1], 1.0);
245
246 // g.push_back(np::gradient(XcY[0], {dx, dy}));
247 // g.push_back(np::gradient(XcY[1], {dx, dy}));
248 std::vector<boost::multi_array<double, 2>> gradf = np::gradient(f, {dx, dy});
249 // auto [gradfx_x, gradfx_y] = np::gradient(f, {dx, dy});
250
251 int i, j;
252 i = 10;
253 j = 20;
254 std::cout << "df/dx of f(x,y) = x^2 + xy at x = " << x[i] << " and y = " << y[j] << " is equal to " << gradf[0][i][j];
255
256 std::cout << "\n";
257}
258
259void test_abs()
260{
261 int nx = 4;
262 int ny = 4;
263 boost::multi_array<double, 1> x = np::linspace(-1, 1, nx);
264 boost::multi_array<double, 1> y = np::linspace(-1, 1, ny);
265 const boost::multi_array<double, 1> axis[2] = {x, y};
266 std::vector<boost::multi_array<double, 2>> XcY = np::meshgrid(axis, false, np::xy);
267 boost::multi_array<double, 2> abs_f = np::abs(XcY[0]);
268 std::cout << "abs_f: \n";
269 for (int i = 0; i < ny; i++)
270 {
271 for (int j = 0; j < nx; j++)
272 {
273 std::cout << abs_f[i][j] << " ";
274 }
275 std::cout << "\n";
276 }
277}
278
279void test_slice()
280{
281 int nx = 4;
282 int ny = 4;
283 boost::multi_array<double, 1> x = np::linspace(-1, 1, nx);
284 boost::multi_array<double, 1> y = np::linspace(-1, 1, ny);
285 const boost::multi_array<double, 1> axis[2] = {x, y};
286 std::vector<boost::multi_array<double, 2>> XcY = np::meshgrid(axis, false, np::xy);
287 boost::multi_array<double, 2> f = np::pow(XcY[0], 2.0) + XcY[0] * np::pow(XcY[1], 1.0);
288 std::cout << "f: \n";
289 for (int i = 0; i < ny; i++)
290 {
291 for (int j = 0; j < nx; j++)
292 {
293 std::cout << f[i][j] << " ";
294 }
295 std::cout << "\n";
296 }
297 std::cout << "f[0]: \n";
298 boost::multi_array<double, 1> f_slice = np::slice(f, 0);
299 for (int i = 0; i < nx; i++)
300 {
301 std::cout << f_slice[i] << " ";
302 }
303 std::cout << "\n";
304
305 std::cout << "f[1]: \n";
306 f_slice = np::slice(f, 1);
307 for (int i = 0; i < ny; i++)
308 {
309 std::cout << f_slice[i] << " ";
310 }
311 std::cout << "\n";
312}
313
314int main()
315{
316 test_gradient();
317 test_meshgrid();
318 test_complex_operations();
319 test_equal();
320 test_basic_operations();
321 test_zeros();
322 test_min_max();
323 test_abs();
324 test_toy_problem();
325 test_slice();
326}
::value constexpr boost::multi_array< T, ND > pow(const boost::multi_array< T, ND > &input_array, const T exponent)
Implements the numpy pow function on multi arrays.
Definition: np.hpp:319
::value constexpr std::vector< boost::multi_array< T, ND > > gradient(boost::multi_array< T, ND > inArray, std::initializer_list< T > args)
Definition: np.hpp:90
::value constexpr std::vector< boost::multi_array< T, ND > > meshgrid(const boost::multi_array< T, 1 >(&cinput)[ND], bool sparsing=false, indexing indexing_type=xy)
Definition: np.hpp:184
::value constexpr boost::multi_array< T, ND > sqrt(const boost::multi_array< T, ND > &input_array)
Implements the numpy sqrt function on multi arrays.
Definition: np.hpp:274
::value constexpr boost::multi_array< T, ND > exp(const boost::multi_array< T, ND > &input_array)
Implements the numpy exp function on multi arrays.
Definition: np.hpp:289
::value constexpr T abs(T input)
Implements the numpy abs function for a scalar.
Definition: np.hpp:463
boost::multi_array< double, 1 > linspace(double start, double stop, long unsigned int num)
Implements the numpy linspace function.
Definition: np.hpp:161
::value constexpr T min(boost::multi_array< T, ND > const &input_array)
Implements the numpy min function for an n-dimensionl multi array.
Definition: np.hpp:419
::value constexpr boost::multi_array< T, ND - 1 > slice(boost::multi_array< T, ND > const &input_array, std::size_t slice_index)
Slices the array through one dimension and returns a ND - 1 dimensional array.
Definition: np.hpp:470
::value constexpr T max(boost::multi_array< T, ND > const &input_array)
Implements the numpy max function for an n-dimensionl multi array.
Definition: np.hpp:384