22#include <boost/multi_array.hpp>
45template <
typename T, std::
size_t N, std::
size_t M = 3,
typename U =
double>
47 using array_type = boost::multi_array<T, M + 1>;
48 using count_type = boost::multi_array<std::size_t, M + 1>;
61 std::array<std::pair<U, U>,
M> limits)
100 void update(std::span<const U> pos, std::span<const T> value) {
101 if (pos.size() !=
M) {
102 throw std::invalid_argument(
"Wrong dimensions for the coordinates");
104 if (value.size() !=
N) {
105 throw std::invalid_argument(
"Wrong dimensions for the value");
107 if (check_limits(pos)) {
108 auto index = calc_bin_index(pos);
109 for (std::size_t i = 0; i <
N; ++i) {
121 std::ranges::transform(
123 [
bin_volume](T v) { return static_cast<T>(v / bin_volume); });
131 auto calc_bin_index(std::span<const U>
const &pos)
const {
132 boost::array<array_index, M + 1> index;
133 for (std::size_t i = 0; i <
M; ++i) {
134 auto const offset =
m_limits[i].first;
136 auto const n_bins =
static_cast<long>(
m_n_bins[i]);
137 auto const bin =
static_cast<long>(std::floor((pos[i] - offset) / size));
141 index[i] =
static_cast<array_index>(std::clamp(
bin, 0l, n_bins - 1l));
149 std::array<U, M> calc_bin_sizes()
const {
151 for (std::size_t i = 0; i <
M; ++i) {
162 bool check_limits(std::span<const U>
const &pos)
const {
165 return std::ranges::all_of(pos, [&
it_limits](
U const value) {
172 std::array<std::size_t, M + 1> m_array_dim()
const {
200template <
typename T, std::
size_t N, std::
size_t M = 3,
typename U =
double>
213 auto const min_r = m_limits[0].first;
217 auto const n_bins_r =
static_cast<array_index
>(m_n_bins[0]);
218 for (array_index i = 0; i <
n_bins_r; i++) {
223 auto *begin = m_array[i].origin();
224 std::ranges::transform(
Histogram in cylindrical coordinates.
void normalize() override
Histogram in Cartesian coordinates.
std::array< U, M > get_bin_sizes() const
Get the bin sizes.
std::array< std::size_t, M > m_n_bins
Number of bins for each dimension.
std::array< U, M > m_bin_sizes
Bin sizes for each dimension.
virtual void normalize()
Normalize histogram.
std::array< std::pair< U, U >, M > m_limits
Min and max values for each dimension.
virtual ~Histogram()=default
count_type m_count
Track the number of total hits per bin entry.
typename array_type::index array_index
std::array< T, N > m_ones
std::vector< std::size_t > get_tot_count() const
Get the histogram count data.
std::vector< T > get_histogram() const
Get the histogram data.
void update(std::span< const U > pos, std::span< const T > value)
Add data to the histogram.
array_type m_array
Histogram data.
std::array< std::pair< U, U >, M > get_limits() const
Get the ranges (min, max) for each dimension.
Histogram(std::array< std::size_t, M > n_bins, std::array< std::pair< U, U >, M > limits)
Histogram constructor.
std::array< std::size_t, M > get_n_bins() const
Get the number of bins for each dimension.
void update(std::span< const U > pos)
Add data to the histogram.
cudaStream_t stream[1]
CUDA streams for parallel computing on CPU and GPU.