chombo-discharge
Loading...
Searching...
No Matches
CD_ParallelOpsImplem.H
Go to the documentation of this file.
1/*
2 * SPDX-FileCopyrightText: 2021-2026 SINTEF Energy Research
3 *
4 * SPDX-License-Identifier: GPL-3.0-or-later
5 */
6
13#ifndef CD_PARALLELOPSIMPLEM_H
14#define CD_PARALLELOPSIMPLEM_H
15
16// Std includes
17#include <limits>
18
19// Chombo includes
20#include <SPMD.H>
21
22// Our includes
23#include <CD_NamespaceHeader.H>
24
25inline void
27{
28 CH_TIME("ParallelOps::barrier");
29
30#ifdef CH_MPI
32#endif
33}
34
36ParallelOps::partition(const int a_N) noexcept
37{
38 CH_TIME("ParallelOps::partition");
39
40#ifdef CH_MPI
41 const int equalChunk = a_N / numProc();
42 const int remainder = a_N % numProc();
43
44 int begin = procID() * equalChunk;
45 int end = begin + equalChunk - 1;
46
47 // Remainder goes to last rank.
48 if (procID() == numProc() - 1) {
49 end += remainder;
50 }
51
52 return std::make_pair(begin, end);
53#else
54 return std::make_pair(0, a_N - 1);
55#endif
56}
57
58inline Real
60{
61 CH_TIME("ParallelOps::min(Real)");
62
63#ifdef CH_MPI
65
67
68 if (result != MPI_SUCCESS) {
69 MayDay::Error("In file ParallelOps::min -- MPI communication error");
70 }
71
72 return ret;
73#else
74 return a_input;
75#endif
76}
77
78inline int
79ParallelOps::min(const int& a_input) noexcept
80{
81 CH_TIME("ParallelOps::min(int)");
82
83#ifdef CH_MPI
84 int ret = a_input;
85
87
88 if (result != MPI_SUCCESS) {
89 MayDay::Error("In file ParallelOps::min -- MPI communication error");
90 }
91 return ret;
92#else
93 return a_input;
94#endif
95}
96
97inline long long int
98ParallelOps::min(const long long int& a_input) noexcept
99{
100 CH_TIME("ParallelOps::min(long long int)");
101
102#ifdef CH_MPI
103 long long int ret = a_input;
104
106
107 if (result != MPI_SUCCESS) {
108 MayDay::Error("In file ParallelOps::min -- MPI communication error");
109 }
110 return ret;
111#else
112 return a_input;
113#endif
114}
115
117ParallelOps::min(const Real& a_val, const RealVect& a_pos) noexcept
118{
119 CH_TIME("ParallelOps::min(Real, RealVect)");
120
121#ifdef CH_MPI
122 const int nProc = numProc();
123
124 Real d = a_val;
125 Real* D = new Real[nProc];
126
127 Real x = a_pos[0];
128 Real* X = new Real[nProc];
129
130 Real y = a_pos[1];
131 Real* Y = new Real[nProc];
132
133#if CH_SPACEDIM == 3
134 Real z = a_pos[2];
135 Real* Z = new Real[nProc];
136#endif
137
141#if CH_SPACEDIM == 3
143#endif
144
145 Real dRet = D[0];
146 Real xRet = X[0];
147 Real yRet = Y[0];
148#if CH_SPACEDIM == 3
149 Real zRet = Z[0];
150#endif
151
152 for (int i = 1; i < nProc; i++) {
153 if (D[i] < dRet) {
154 dRet = D[i];
155 xRet = X[i];
156 yRet = Y[i];
157#if CH_SPACEDIM == 3
158 zRet = Z[i];
159#endif
160 }
161 }
162
163 delete[] D;
164 delete[] X;
165 delete[] Y;
166#if CH_SPACEDIM == 3
167 delete[] Z;
168#endif
169
171#else
172 return std::make_pair(a_val, a_pos);
173#endif
174}
175
176inline Real
178{
179 CH_TIME("ParallelOps::max(Real)");
180
181#ifdef CH_MPI
182 Real ret = a_input;
183
185 if (result != MPI_SUCCESS) {
186 MayDay::Error("In file ParallelOps::max -- MPI communication error");
187 }
188
189 return ret;
190#else
191 return a_input;
192#endif
193}
194
195inline int
196ParallelOps::max(const int& a_input) noexcept
197{
198 CH_TIME("ParallelOps::max(int)");
199
200#ifdef CH_MPI
201 int ret = a_input;
202
204
205 if (result != MPI_SUCCESS) {
206 MayDay::Error("In file ParallelOps::max -- MPI communication error");
207 }
208 return ret;
209#else
210 return a_input;
211#endif
212}
213
214inline long long
215ParallelOps::max(const long long& a_input) noexcept
216{
217 CH_TIME("ParallelOps::max(long long)");
218
219#ifdef CH_MPI
220 long long ret = a_input;
221
223
224 if (result != MPI_SUCCESS) {
225 MayDay::Error("In file ParallelOps::max -- MPI communication error");
226 }
227 return ret;
228#else
229 return a_input;
230#endif
231}
232
234ParallelOps::max(const Real& a_val, const RealVect& a_pos) noexcept
235{
236 CH_TIME("ParallelOps::max(Real, RealVect)");
237
238#ifdef CH_MPI
239 const int nProc = numProc();
240
241 Real d = a_val;
242 Real* D = new Real[nProc];
243
244 Real x = a_pos[0];
245 Real* X = new Real[nProc];
246
247 Real y = a_pos[1];
248 Real* Y = new Real[nProc];
249
250#if CH_SPACEDIM == 3
251 Real z = a_pos[2];
252 Real* Z = new Real[nProc];
253#endif
254
258#if CH_SPACEDIM == 3
260#endif
261
262 Real dRet = D[0];
263 Real xRet = X[0];
264 Real yRet = Y[0];
265#if CH_SPACEDIM == 3
266 Real zRet = Z[0];
267#endif
268
269 for (int i = 1; i < nProc; i++) {
270 if (D[i] > dRet) {
271 dRet = D[i];
272 xRet = X[i];
273 yRet = Y[i];
274#if CH_SPACEDIM == 3
275 zRet = Z[i];
276#endif
277 }
278 }
279
280 delete[] D;
281 delete[] X;
282 delete[] Y;
283#if CH_SPACEDIM == 3
284 delete[] Z;
285#endif
286
288#else
289 return std::make_pair(a_val, a_pos);
290#endif
291}
292
295{
296 CH_TIME("ParallelOps::maxRank(Real)");
297
298#ifdef CH_MPI
299 const int nProc = numProc();
300
301 Real* values = new Real[nProc];
302
304
305 int irank = -1;
306 Real maxVal = -std::numeric_limits<Real>::max();
307
308 for (int i = 0; i < nProc; i++) {
309 if (values[i] > maxVal) {
310 irank = i;
311 maxVal = values[i];
312 }
313 }
314
315 delete[] values;
316
317 return std::make_pair(maxVal, irank);
318#else
319 return std::make_pair(a_val, 0);
320#endif
321}
322
325{
326 CH_TIME("ParallelOps::minRank(Real)");
327
328#ifdef CH_MPI
329 const int nProc = numProc();
330
331 Real* values = new Real[nProc];
332
334
335 int irank = -1;
336 Real maxVal = std::numeric_limits<Real>::max();
337
338 for (int i = 0; i < nProc; i++) {
339 if (values[i] < maxVal) {
340 irank = i;
341 maxVal = values[i];
342 }
343 }
344
345 delete[] values;
346
347 return std::make_pair(maxVal, irank);
348#else
349 return std::make_pair(a_val, 0);
350#endif
351}
352
353inline Real
355{
356 CH_TIME("ParallelOps::sum(Real)");
357
358#ifdef CH_MPI
359 Real ret = 0.0;
360
362 if (result != MPI_SUCCESS) {
363 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
364 }
365
366 return ret;
367#else
368 return a_value;
369#endif
370}
371
372inline int
373ParallelOps::sum(const int& a_value) noexcept
374{
375 CH_TIME("ParallelOps::sum(Real)");
376
377#ifdef CH_MPI
378 int ret = 0;
379
381 if (result != MPI_SUCCESS) {
382 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
383 }
384
385 return ret;
386#else
387 return a_value;
388#endif
389}
390
391inline long
392ParallelOps::sum(const long& a_value) noexcept
393{
394 CH_TIME("ParallelOps::sum(long)");
395
396#ifdef CH_MPI
397 long ret = 0;
398
400 if (result != MPI_SUCCESS) {
401 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
402 }
403
404 return ret;
405#else
406 return a_value;
407#endif
408}
409
410inline long long
411ParallelOps::sum(const long long& a_value) noexcept
412{
413 CH_TIME("ParallelOps::sum(long long)");
414
415#ifdef CH_MPI
416 long long ret = 0;
417
419 if (result != MPI_SUCCESS) {
420 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
421 }
422
423 return ret;
424#else
425 return a_value;
426#endif
427}
428
429inline unsigned long long
430ParallelOps::sum(const unsigned long long& a_value) noexcept
431{
432 CH_TIME("ParallelOps::sum(unsigned long long)");
433
434#ifdef CH_MPI
435 unsigned long long ret = 0;
436
438 if (result != MPI_SUCCESS) {
439 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
440 }
441
442 return ret;
443#else
444 return a_value;
445#endif
446}
447
448inline void
450{
451 CH_TIME("ParallelOps::sum(Real)");
452
453#ifdef CH_MPI
455 if (result != MPI_SUCCESS) {
456 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
457 }
458#endif
459}
460
461inline void
463{
464 CH_TIME("ParallelOps::sum(int)");
465
466#ifdef CH_MPI
468 if (result != MPI_SUCCESS) {
469 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
470 }
471#endif
472}
473
474inline void
476{
477 CH_TIME("ParallelOps::sum(long int)");
478
479#ifdef CH_MPI
481 if (result != MPI_SUCCESS) {
482 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
483 }
484#endif
485}
486
487inline void
489{
490 CH_TIME("ParallelOps::sum(long long int)");
491
492#ifdef CH_MPI
494 if (result != MPI_SUCCESS) {
495 MayDay::Error("In file ParallelOps::sum -- MPI communication error");
496 }
497#endif
498}
499
500inline Real
502{
503 CH_TIME("ParallelOps::average(Real)");
504
505#ifdef CH_MPI
506 return ParallelOps::sum(a_val) / numProc();
507#else
508 return a_val;
509#endif
510}
511
512inline Real
514{
515 CH_TIME("ParallelOps::standardDeviation(Real)");
516
517#ifdef CH_MPI
518 const int nProc = numProc();
519
521
522 Real* values = new Real[nProc];
523
525
526 Real sigma = 0.0;
527 for (int i = 0; i < nProc; i++) {
528 sigma += std::pow(values[i] - average, 2);
529 }
530
531 delete[] values;
532
533 return sqrt(sigma / nProc);
534#else
535 return 0.0;
536#endif
537}
538
539inline Vector<int>
541{
542 CH_TIME("ParallelOps::gather(int)");
543
544#ifdef CH_MPI
546
547 MPI_Allgather(&a_localValue, 1, MPI_INT, ret.stdVector().data(), 1, MPI_INT, Chombo_MPI::comm);
548
549 return ret;
550#else
551 return Vector<int>(1, a_localValue);
552#endif
553}
554
555inline Vector<Real>
557{
558 CH_TIME("ParallelOps::gather(Real)");
559
560#ifdef CH_MPI
562
564
565 return ret;
566#else
567 return Vector<Real>(1, a_localValue);
568#endif
569}
570
571#include <CD_NamespaceFooter.H>
572
573#endif
Base class for a tracer particle solver. This solver can advance particles in a pre-defined velocity ...
Definition CD_TracerParticleSolver.H:38
TracerParticleSolver()
Default constructor.
Definition CD_TracerParticleSolverImplem.H:26
Real max(const Real &a_input) noexcept
Get the maximum of the input, reduced over MPI ranks (in the Chombo communicator)
Definition CD_ParallelOpsImplem.H:177
std::pair< Real, int > maxRank(const Real &a_val) noexcept
Get the maximum value and the rank having the maximum value.
Definition CD_ParallelOpsImplem.H:294
Real average(const Real &a_val) noexcept
Compute the average (across MPI ranks) of the input value.
Definition CD_ParallelOpsImplem.H:501
Real standardDeviation(const Real &a_value) noexcept
Compute the standard deviation of the input value.
Definition CD_ParallelOpsImplem.H:513
Vector< int > gather(const int &a_localValue) noexcept
Gather local values – return a vector of local values.
Definition CD_ParallelOpsImplem.H:540
std::pair< Real, int > minRank(const Real &a_val) noexcept
Get the minimum value and the rank having the minimum value.
Definition CD_ParallelOpsImplem.H:324
Real min(const Real &a_input) noexcept
Get the minimum of the input, reduced over MPI ranks (in the Chombo communicator)
Definition CD_ParallelOpsImplem.H:59
Real sum(const Real &a_value) noexcept
Compute the sum across all MPI ranks.
Definition CD_ParallelOpsImplem.H:354
std::pair< int, int > partition(int a_N) noexcept
Partition the input number such that each MPI rank gets an equal chunk. We assume that N is the lengt...
Definition CD_ParallelOpsImplem.H:36
void barrier() noexcept
MPI barrier.
Definition CD_ParallelOpsImplem.H:26