1
1
#include " PrepareDerivatives.hpp"
2
2
3
+ #include < eve/module/core.hpp>
4
+
3
5
namespace ahr {
4
6
5
7
void PrepareDerivatives::operator ()(View::C_XY const &in, DxDy<View::C_XY> out) const {
@@ -9,4 +11,48 @@ void PrepareDerivatives::operator()(View::C_XY const &in, DxDy<View::C_XY> out)
9
11
});
10
12
}
11
13
14
+ void PrepareDerivativesVector::operator ()(View::C_XY const &in, DxDy<View::C_XY> out) const {
15
+ eve::logical<VIdx> const even_mask{[](int idx, int ) { return idx % 2 == 0 ; }};
16
+ VReal const kx_v_init{[](int idx, int ) { return Real (idx / 2 ); }};
17
+ for (Dim ky = 0 ; ky < grid.KY ; ky += KY_TILE) {
18
+ // broadcast ky values
19
+ using TileReal = std::array<VReal, KY_TILE>;
20
+ TileReal ky_v;
21
+ for (Dim tile_ky = 0 ; tile_ky < KY_TILE; ++tile_ky) {
22
+ ky_v[tile_ky] = ky_ (ky + tile_ky);
23
+ }
24
+
25
+ // Initialize kx values
26
+ VReal kx_v = kx_v_init;
27
+
28
+ Dim kx = 0 ;
29
+ for (; kx <= grid.KX - C_WIDTH; kx += C_WIDTH, kx_v += C_WIDTH) {
30
+ auto input = [&](int i) { return (Real *)&in (kx, ky + i); };
31
+ auto out_dx = [&](int i) { return (Real *)&out.DX (kx, ky + i); };
32
+ auto out_dy = [&](int i) { return (Real *)&out.DY (kx, ky + i); };
33
+
34
+ for (int i = 0 ; i < KY_TILE; ++i) {
35
+ auto in_v = VReal{input (i)};
36
+ // (a + bi) * i -> (-b + ai)
37
+ // swap real and imaginary parts
38
+ auto swapped = eve::swap_adjacent (in_v);
39
+ // selectively negate
40
+ auto mul_with_i = eve::minus[even_mask](swapped);
41
+ // normalize
42
+ auto in_norm = mul_with_i * XYNorm;
43
+
44
+ eve::store (kx_v * in_norm, out_dx (i));
45
+ eve::store (ky_v[i] * in_norm, out_dy (i));
46
+ }
47
+ }
48
+
49
+ // tail
50
+ for (; kx < grid.KX ; ++kx) {
51
+ for (int i = 0 ; i < KY_TILE; ++i) {
52
+ out.DX (kx, ky + i) = kx_ (kx) * 1i * in (kx, ky + i) * XYNorm;
53
+ out.DY (kx, ky + i) = ky_ (ky + i) * 1i * in (kx, ky + i) * XYNorm;
54
+ }
55
+ }
56
+ }
57
+ }
12
58
} // namespace ahr
0 commit comments