ESPResSo
Extensible Simulation Package for Research on Soft Matter Systems
Loading...
Searching...
No Matches
field_layout_helpers.hpp
Go to the documentation of this file.
1
/*
2
* Copyright (C) 2024-2025 The ESPResSo project
3
*
4
* This file is part of ESPResSo.
5
*
6
* ESPResSo is free software: you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
* the Free Software Foundation, either version 3 of the License, or
9
* (at your option) any later version.
10
*
11
* ESPResSo is distributed in the hope that it will be useful,
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
* GNU General Public License for more details.
15
*
16
* You should have received a copy of the GNU General Public License
17
* along with this program. If not, see <http://www.gnu.org/licenses/>.
18
*/
19
20
#pragma once
21
22
#include "
for_each_3d.hpp
"
23
24
#include <
utils/Vector.hpp
>
25
#include <
utils/index.hpp
>
26
27
#include <algorithm>
28
#include <cassert>
29
#include <complex>
30
#include <cstddef>
31
#include <iterator>
32
#include <span>
33
#include <type_traits>
34
#include <vector>
35
36
// Function to extract a 3D block from the halo field
37
template
<
Utils::MemoryOrder
memory_order
,
38
Utils::MemoryOrder
output_memory_order
,
typename
Container>
39
auto
extract_block
(Container
const
&
in_array
,
Utils::Vector3i
const
&
dimensions
,
40
Utils::Vector3i
const
&start,
Utils::Vector3i
const
&stop) {
41
// Calculate the size of the block excluding halo regions
42
auto
const
block_dim
= stop - start;
43
auto
const
size =
static_cast<
std::size_t
>
(
Utils::product
(
block_dim
));
44
45
// Output vector to hold the block
46
std::vector<typename Container::value_type>
out_array
(size);
47
48
// Extract the block
49
if
constexpr
(
memory_order
==
Utils::MemoryOrder::ROW_MAJOR
and
50
output_memory_order
==
Utils::MemoryOrder::ROW_MAJOR
) {
51
auto
const
plane_src
=
dimensions
[2] *
dimensions
[1];
52
auto
const
lane_src
=
dimensions
[2];
53
auto
const
lane_dst
=
block_dim
[2];
54
auto
src
=
in_array
.data();
55
auto
dst
=
out_array
.begin();
56
for
(
int
x = start[0]; x < stop[0]; ++x) {
57
for
(
int
y = start[1]; y < stop[1]; ++y) {
58
auto
const
offset_src
= x *
plane_src
+ y *
lane_src
+ start[2];
59
std::copy_n(
src
+
offset_src
,
lane_dst
,
dst
);
60
std::advance(
dst
,
lane_dst
);
61
}
62
}
63
}
else
{
64
for_each_3d_lin<output_memory_order>
(
65
start, stop, [&](
Utils::Vector3i
const
&
indices
,
int
out_index
) {
66
// Compute indices for input and output arrays
67
auto
const
in_index
=
68
Utils::get_linear_index<memory_order>(
indices
,
dimensions
);
69
assert
(
out_index
== Utils::get_linear_index<output_memory_order>(
70
indices
- start,
block_dim
));
71
// Copy the value
72
out_array
[
out_index
] =
in_array
[
in_index
];
73
});
74
}
75
76
return
out_array
;
77
}
78
79
/** @brief Pad a 3D matrix with zeros to restore halo regions. */
80
template
<
Utils::MemoryOrder
memory_order
,
81
Utils::MemoryOrder
output_memory_order
,
typename
T>
82
auto
pad_with_zeros_discard_imag
(std::span<T>
cropped_array
,
83
Utils::Vector3i
const
&
cropped_dim
,
84
Utils::Vector3i
const
&
pad_left
,
85
Utils::Vector3i
const
&
pad_right
) {
86
87
using
value_type =
decltype
(std::real(std::declval<T>()));
88
auto
constexpr
get_real
= [](
auto
const
&v) {
return
std::real(v); };
89
// Calculate dimensions and strides
90
auto
const
padded_dim
=
cropped_dim
+
pad_left
+
pad_right
;
91
// Output vector to hold the padded field (initialized with zeros)
92
std::vector<value_type>
padded_array
(
Utils::product
(
padded_dim
));
93
94
// Fill in the original cropped field into the padded array by chunks
95
if
constexpr
(
memory_order
==
Utils::MemoryOrder::ROW_MAJOR
and
96
output_memory_order
==
Utils::MemoryOrder::ROW_MAJOR
) {
97
auto
const
plane_dst
=
padded_dim
[2] *
padded_dim
[1];
98
auto
const
lane_dst
=
padded_dim
[2];
99
auto
const
lane_src
=
cropped_dim
[2];
100
auto
const
base_offset_dst
=
101
pad_left
[0] *
plane_dst
+
pad_left
[1] *
lane_dst
+
pad_left
[2];
102
auto
dst
=
padded_array
.data();
103
auto
src
=
cropped_array
.begin();
104
for
(
int
x = 0; x <
cropped_dim
[0]; ++x) {
105
for
(
int
y = 0; y <
cropped_dim
[1]; ++y) {
106
auto
const
offset_dst
=
base_offset_dst
+ x *
plane_dst
+ y *
lane_dst
;
107
if
constexpr
(std::is_floating_point_v<T>) {
108
std::copy_n(
src
,
lane_src
,
dst
+
offset_dst
);
109
}
else
{
110
std::transform(
src
,
src
+
lane_src
,
dst
+
offset_dst
,
get_real
);
111
}
112
std::advance(
src
,
lane_src
);
113
}
114
}
115
}
else
{
116
for_each_3d_lin<memory_order>
(
117
Utils::Vector3i
{0, 0, 0},
cropped_dim
,
118
[&](
Utils::Vector3i
const
&
indices
,
int
in_index
) {
119
// Compute indices for input and output arrays
120
auto
const
out_index
= Utils::get_linear_index<output_memory_order>(
121
indices
+
pad_left
,
padded_dim
);
122
// Copy the value
123
padded_array
[
out_index
] = std::real(
cropped_array
[
in_index
]);
124
});
125
}
126
127
return
padded_array
;
128
}
Vector.hpp
Vector implementation and trait types for boost qvm interoperability.
Utils::Vector
Definition
Vector.hpp:50
stream
cudaStream_t stream[1]
CUDA streams for parallel computing on CPU and GPU.
Definition
common_cuda.cu:34
pad_with_zeros_discard_imag
auto pad_with_zeros_discard_imag(std::span< T > cropped_array, Utils::Vector3i const &cropped_dim, Utils::Vector3i const &pad_left, Utils::Vector3i const &pad_right)
Pad a 3D matrix with zeros to restore halo regions.
Definition
field_layout_helpers.hpp:82
extract_block
auto extract_block(Container const &in_array, Utils::Vector3i const &dimensions, Utils::Vector3i const &start, Utils::Vector3i const &stop)
Definition
field_layout_helpers.hpp:39
for_each_3d.hpp
index.hpp
Utils::product
T product(Vector< T, N > const &v)
Definition
Vector.hpp:373
Utils::MemoryOrder
MemoryOrder
Definition
index.hpp:32
Utils::MemoryOrder::ROW_MAJOR
@ ROW_MAJOR
src
core
p3m
field_layout_helpers.hpp
Generated on Mon Dec 8 2025 02:32:29 for ESPResSo by
1.9.8