Loading [MathJax]/extensions/TeX/AMSmath.js
ESPResSo
Extensible Simulation Package for Research on Soft Matter Systems
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages Concepts
sampling.hpp
Go to the documentation of this file.
1/*
2 * Copyright (C) 2010-2022 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 "utils/Vector.hpp"
24#include "utils/math/sqr.hpp"
25
26#include <algorithm>
27#include <cmath>
28#include <cstddef>
29#include <iterator>
30#include <utility>
31#include <vector>
32
33namespace Utils {
34
35/**
36 * @brief Generate sampling positions for a cylindrical histogram.
37 * @param r_limits Range for radial coordinate as std::pair.
38 * @param phi_limits Range for azimuthal angle as std::pair.
39 * @param z_limits Range for z coordinate as std::pair.
40 * @param n_r_bins Number of bins in radial direction.
41 * @param n_phi_bins Number of bins in azimuthal direction.
42 * @param n_z_bins Number of bins in z direction.
43 * @param sampling_density The number of samples per unit volume.
44 * @retval Cartesian sampling coordinates.
45 */
47 std::pair<double, double> const &r_limits,
48 std::pair<double, double> const &phi_limits,
49 std::pair<double, double> const &z_limits, std::size_t n_r_bins,
50 std::size_t n_phi_bins, std::size_t n_z_bins, double sampling_density) {
51 auto constexpr endpoint = false;
52 auto const delta_r =
53 (r_limits.second - r_limits.first) / static_cast<double>(n_r_bins);
54 auto const delta_phi =
55 (phi_limits.second - phi_limits.first) / static_cast<double>(n_phi_bins);
56
57 // For the smallest bin we chose samples along the z-direction for a single
58 // azimuthal angle per bin such that we fulfill the sampling density
59 // requirement.
60 auto const smallest_bin_volume =
61 Utils::sqr(r_limits.first + delta_r) * delta_phi / 2.;
62 auto const min_n_samples =
63 std::max(n_z_bins, static_cast<std::size_t>(std::round(
64 smallest_bin_volume * sampling_density)));
65 auto const delta_z =
66 (z_limits.second - z_limits.first) / static_cast<double>(min_n_samples);
67
68 std::vector<double> r_range;
69 std::ranges::copy(make_lin_space(r_limits.first + .5 * delta_r,
70 r_limits.second, n_r_bins, endpoint),
71 std::back_inserter(r_range));
72
73 auto const phi_range =
74 make_lin_space(phi_limits.first + .5 * delta_phi, phi_limits.second,
75 n_phi_bins, endpoint);
76 auto const z_range = make_lin_space(z_limits.first + .5 * delta_z,
77 z_limits.second, min_n_samples, endpoint);
78
79 // Create the sampling positions for the innermost bin.
80 std::vector<Vector3d> sampling_positions;
81 for (auto const z : z_range) {
82 for (auto const phi : phi_range) {
83 sampling_positions.push_back(Vector3d{{r_range.front(), phi, z}});
84 }
85 }
86
87 // Scale the number of samples for larger bins
88 auto phis = [n_phi_bins, phi_limits](long r_bin) {
89 auto const phis_range = make_lin_space(
90 phi_limits.first, phi_limits.second,
91 n_phi_bins * (static_cast<std::size_t>(r_bin) + 1u), endpoint);
92 return phis_range;
93 };
94 // Calculate the sampling positions
95 // Along z
96 for (auto const z : z_range) {
97 // Along r
98 for (auto r_it = ++r_range.begin(); r_it != r_range.end(); ++r_it) {
99 // Along phi
100 for (auto const phi : phis(std::distance(r_range.begin(), r_it))) {
101 sampling_positions.push_back(Vector3d{{*r_it, phi, z}});
102 }
103 }
104 }
105
106 return sampling_positions;
107}
108
109} // namespace Utils
Vector implementation and trait types for boost qvm interoperability.
std::vector< Vector3d > get_cylindrical_sampling_positions(std::pair< double, double > const &r_limits, std::pair< double, double > const &phi_limits, std::pair< double, double > const &z_limits, std::size_t n_r_bins, std::size_t n_phi_bins, std::size_t n_z_bins, double sampling_density)
Generate sampling positions for a cylindrical histogram.
Definition sampling.hpp:46
auto make_lin_space(T start, T stop, std::size_t number, bool endpoint=true)
Equally spaced values in interval.
DEVICE_QUALIFIER constexpr T sqr(T x)
Calculates the SQuaRe of x.
Definition sqr.hpp:28
DEVICE_QUALIFIER constexpr reference front()
Definition Array.hpp:122