1#ifndef TATOOINE_CHUNKED_MULTIDIM_ARRAY_H
2#define TATOOINE_CHUNKED_MULTIDIM_ARRAY_H
13#include <boost/range/algorithm.hpp>
25template <
typename T,
typename GlobalIndexOrder = x_fastest,
26 typename LocalIndexOrder = GlobalIndexOrder>
60 template <range SizeRange, range ChunkSizeRange>
61 requires(is_integral<typename std::decay_t<SizeRange>::value_type>) &&
62 (
is_integral<
typename std::decay_t<ChunkSizeRange>::value_type>)
69 template <range Range>
74 for (
auto const& d : data) {
79 template <can_read<this_type> Reader>
86 template <range SizeRange>
88 is_integral<typename std::decay_t<SizeRange>::value_type>) {
95 for (; size_it <
end(
size); ++size_it, ++chunk_size_it) {
97 static_cast<double>(*size_it) /
static_cast<double>(*chunk_size_it)));
103 template <range SizeRange, range ChunkSizeRange>
109 auto i = std::size_t{};
111 s = std::min(s,
static_cast<std::size_t
>(
size[i++]));
117 return resize(std::vector{
static_cast<std::size_t
>(sizes)...});
120 template <
typename Tensor,
integral Int, std::
size_t N>
124 for (std::size_t i = 0; i < N; ++i) {
130 template <
integral Int, std::
size_t N>
131 auto resize(std::array<Int, N>
const& v) {
137 template <std::size_t... Seq>
139 std::size_t plain_chunk_index, std::index_sequence<Seq...>,
141 assert(
m_chunks[plain_chunk_index] !=
nullptr);
143 return m_chunks[plain_chunk_index]->plain_index(
149 std::size_t plain_chunk_index,
integral auto const... is)
const {
150 assert(
m_chunks[plain_chunk_index] !=
nullptr);
153 plain_chunk_index, std::make_index_sequence<
sizeof...(is)>{}, is...);
157 template <std::size_t... Seq>
159 std::index_sequence<Seq...> ,
integral auto const... is)
const {
169 std::make_index_sequence<
sizeof...(is)>{}, is...);
173 template <std::size_t... Seq>
175 std::index_sequence<Seq...>,
integral auto const... is)
const {
183 std::make_index_sequence<
sizeof...(is)>{}, is...);
186 template <
integral Int>
196 template <std::size_t... Seq>
207 std::make_index_sequence<
sizeof...(is)>{}, is...);
210 template <
integral Int>
219 template <
integral Int>
229 integral auto const... chunk_indices)
const {
234 template <
integral Int>
236 std::vector<Int>
const& chunk_indices)
const {
242 integral auto const... chunk_indices)
const ->
auto const& {
243 if constexpr (
sizeof...(chunk_indices) == 0) {
253 integral auto const... chunk_indices)
const {
254 if constexpr (
sizeof...(chunk_indices) == 0) {
255 return m_chunks[chunk_index0] ==
nullptr;
259 chunk_index0, chunk_indices...)] ==
nullptr;
264 for (std::size_t i = 0; i <
num_chunks(); ++i) {
270 std::vector<std::size_t>
const& multi_indices)
const
294 integral auto const... chunk_indices)
const
300 std::vector<std::size_t>{chunk_index0, chunk_index1, chunk_indices...});
304 integral auto const... chunk_indices)
const {
305 if constexpr (
sizeof...(chunk_indices) == 0) {
315 for (
auto const& chunk : other.m_chunks) {
317 *(chunk_it++) = std::make_unique<chunk_t>(*chunk);
324 if (chunk !=
nullptr) {
357 std::size_t
const plain_internal_index =
367 static constexpr T t{};
370 std::size_t
const plain_internal_index =
375 template <
typename Tensor, std::
size_t N,
integral S>
378 [
this](
auto const... is) ->
decltype(
auto) {
return at(is...); },
382 template <
integral S, std::
size_t N>
383 auto at(std::array<S, N>
const& is) -> T& {
385 [
this](
auto const... is) ->
decltype(
auto) {
return at(is...); },
389 template <
integral S>
390 auto at(std::vector<S>
const& is) -> T& {
393 std::size_t
const plain_chunk_index =
398 return m_chunks[plain_chunk_index]->at(
402 template <
integral S>
403 auto at(std::vector<S>
const& is)
const -> T
const& {
408 global_is[i] /= is[i];
417 local_is[i] %= is[i];
419 return m_chunks[plain_chunk_index]->at(local_is);
432 template <
typename Tensor, std::
size_t N,
integral S>
437 template <
integral S, std::
size_t N>
442 template <
integral S, std::
size_t N>
443 auto operator()(std::array<S, N>
const& is)
const -> T
const& {
447 template <
integral S, std::
size_t N>
448 auto at(std::array<S, N>
const& is)
const -> T
const& {
450 [
this](
auto const... is) ->
decltype(
auto) {
return at(is...); },
472 template <
typename RandomEngine = std::mt19937_64>
473 requires is_arithmetic<T>
auto randu(
475 RandomEngine&& random_engine = RandomEngine{std::random_device{}()})
479 chunk = std::make_unique<chunk_t>();
481 chunk->randu(
min,
max, std::forward<RandomEngine>(random_engine));
486 T
min = std::numeric_limits<T>::max();
487 for (
auto const& chunk :
m_chunks) {
489 min = std::min(
min, *chunk->min_element());
496 T
max = -std::numeric_limits<T>::max();
497 for (
auto const& chunk :
m_chunks) {
499 max = std::max(
max, *chunk->max_element());
506 std::pair minmax{std::numeric_limits<T>::max(),
507 -std::numeric_limits<T>::max()};
508 auto& [
min,
max] = minmax;
509 for (
auto const& chunk :
m_chunks) {
511 auto [chunkmin, chunkmax] = chunk->minmax_element();
512 if (!std::isinf(*chunkmin) && !std::isnan(*chunkmin)) {
513 min = std::min(
min, *chunkmin);
515 if (!std::isinf(*chunkmax) && !std::isnan(*chunkmax)) {
516 max = std::max(
max, *chunkmax);
525 auto normalizer = 1.0 / (
max -
min);
527 for (
auto const& chunk :
m_chunks) {
529 for (
auto& val : *chunk) {
530 val = (val -
min) * normalizer;
538 template <
typename Iteration>
541 std::vector<std::pair<std::size_t, std::size_t>>(
num_dimensions());
543 std::vector<std::pair<std::size_t, std::size_t>>(
num_dimensions());
551 [&](std::vector<std::size_t>
const& outer_indices) {
564 [&](std::vector<std::size_t>
const& inner_indices) {
565 auto global_indices =
573 iteration(global_indices);
Definition: dynamic_multidim_array.h:18
Definition: dynamic_multidim_size.h:16
auto constexpr plain_index(integral auto const ... indices) const
Definition: dynamic_multidim_size.h:149
auto constexpr in_range(integral auto const ... indices) const
Definition: dynamic_multidim_size.h:130
auto constexpr multi_index(std::size_t const gi) const
Definition: dynamic_multidim_size.h:161
auto num_dimensions() const
Definition: dynamic_multidim_size.h:105
auto resize(integral auto const ... size) -> void
Definition: dynamic_multidim_size.h:116
auto num_components() const
Definition: dynamic_multidim_size.h:111
Definition: concepts.h:21
Definition: algorithm.h:6
auto begin(Range &&range)
Definition: iterator_facade.h:318
typename value_type_impl< T >::type value_type
Definition: type_traits.h:280
auto end(Range &&range)
Definition: iterator_facade.h:322
static constexpr auto is_integral
Definition: type_traits.h:83
static constexpr auto is_arithmetic
Definition: type_traits.h:80
constexpr auto max(A &&a, B &&b)
Definition: math.h:20
constexpr auto min(A &&a, B &&b)
Definition: math.h:15
constexpr decltype(auto) invoke_unpacked(F &&f)
All arguments are bound -> just call f.
Definition: invoke_unpacked.h:15
constexpr auto for_loop(Iteration &&iteration, execution_policy::sequential_t, Ranges(&&... ranges)[2]) -> void
Use this function for creating a sequential nested loop.
Definition: for_loop.h:336
Definition: base_tensor.h:23
Definition: chunked_multidim_array.h:27
auto internal_chunk_indices_from_global_indices(integral auto const ... is) const
Definition: chunked_multidim_array.h:180
LocalIndexOrder local_index_order_t
Definition: chunked_multidim_array.h:36
auto resize(SizeRange &&size, ChunkSizeRange &&chunk_size)
Definition: chunked_multidim_array.h:104
auto global_indices_from_chunk_indices(std::vector< Int > is) const
Definition: chunked_multidim_array.h:220
auto internal_chunk_size() const
Definition: chunked_multidim_array.h:335
auto at(std::vector< S > const &is) const -> T const &
Definition: chunked_multidim_array.h:403
auto constexpr in_range(integral auto const ... indices) const
Definition: dynamic_multidim_size.h:130
auto internal_chunk_size(std::size_t const i) const
Definition: chunked_multidim_array.h:336
chunk_ptr_field_t m_chunks
Definition: chunked_multidim_array.h:49
chunked_multidim_array(Range &&data, std::vector< std::size_t > const &size, std::vector< std::size_t > const &chunk_size)
Definition: chunked_multidim_array.h:70
auto resize(base_tensor< Tensor, Int, N > const &v) -> void
Definition: chunked_multidim_array.h:121
auto plain_chunk_index_from_chunk_indices(integral auto const ... chunk_indices) const
Definition: chunked_multidim_array.h:228
auto resize(integral auto const ... sizes) -> void
Definition: chunked_multidim_array.h:116
auto chunk_indices_from_global_indices(std::index_sequence< Seq... >, integral auto const ... is) const
Definition: chunked_multidim_array.h:197
auto internal_chunk_indices_from_global_indices(std::index_sequence< Seq... >, integral auto const ... is) const
Definition: chunked_multidim_array.h:174
auto operator()(integral auto const ... is) const -> T const &
Definition: chunked_multidim_array.h:427
auto chunk_at(integral auto const chunk_index0, integral auto const ... chunk_indices) const -> auto const &
Definition: chunked_multidim_array.h:241
auto chunk_size() const
Definition: chunked_multidim_array.h:332
auto plain_chunk_index_from_chunk_indices(std::vector< Int > const &chunk_indices) const
Definition: chunked_multidim_array.h:235
auto at(std::array< S, N > const &is) -> T &
Definition: chunked_multidim_array.h:383
auto create_chunk_at(std::size_t const plain_chunk_index, std::vector< std::size_t > const &multi_indices) const -> auto const &
Definition: chunked_multidim_array.h:269
auto max_value() const
Definition: chunked_multidim_array.h:495
auto operator[](std::size_t plain_index) const -> T const &
Definition: chunked_multidim_array.h:345
auto create_all_chunks() const -> void
Definition: chunked_multidim_array.h:263
auto at(integral auto const ... is) -> T &
Definition: chunked_multidim_array.h:350
auto chunk_size(std::size_t i) const
Definition: chunked_multidim_array.h:333
auto plain_internal_chunk_index_from_global_indices(std::size_t plain_chunk_index, std::index_sequence< Seq... >, integral auto const ... is) const
Definition: chunked_multidim_array.h:138
auto randu(T min=0, T max=1, RandomEngine &&random_engine=RandomEngine{std::random_device{}()}) -> void
Definition: chunked_multidim_array.h:473
auto chunk_at_is_null(integral auto const chunk_index0, integral auto const ... chunk_indices) const
Definition: chunked_multidim_array.h:252
auto constexpr multi_index(std::size_t const gi) const
Definition: dynamic_multidim_size.h:161
auto create_chunk_at(integral auto const chunk_index0, integral auto const chunk_index1, integral auto const ... chunk_indices) const -> auto const &
Definition: chunked_multidim_array.h:292
std::vector< std::size_t > m_internal_chunk_size
Definition: chunked_multidim_array.h:45
auto min_value() const
Definition: chunked_multidim_array.h:485
auto plain_chunk_index_from_global_indices(integral auto const ... is) const
Definition: chunked_multidim_array.h:166
auto at(std::vector< S > const &is) -> T &
Definition: chunked_multidim_array.h:390
auto normalize() -> void
Definition: chunked_multidim_array.h:523
T value_type
Definition: chunked_multidim_array.h:29
auto size() const -> auto const &
Definition: dynamic_multidim_size.h:107
GlobalIndexOrder global_index_order_t
Definition: chunked_multidim_array.h:35
auto num_chunks() const
Definition: chunked_multidim_array.h:330
auto clear()
Definition: chunked_multidim_array.h:322
auto num_dimensions() const
Definition: dynamic_multidim_size.h:105
chunked_multidim_array(chunked_multidim_array const &other)
Definition: chunked_multidim_array.h:52
auto operator()(base_tensor< Tensor, S, N > const &is) -> T &
Definition: chunked_multidim_array.h:433
std::vector< chunk_ptr_t > chunk_ptr_field_t
Definition: chunked_multidim_array.h:34
dynamic_multidim_size< LocalIndexOrder > m_chunk_structure
Definition: chunked_multidim_array.h:46
auto copy_chunks(chunked_multidim_array const &other) -> void
Definition: chunked_multidim_array.h:313
auto operator()(std::array< S, N > const &is) -> T &
Definition: chunked_multidim_array.h:438
auto operator()(std::array< S, N > const &is) const -> T const &
Definition: chunked_multidim_array.h:443
auto internal_chunk_indices_from_global_indices(std::vector< Int > is) const
Definition: chunked_multidim_array.h:187
auto chunk_indices_from_global_indices(std::vector< Int > is) const
Definition: chunked_multidim_array.h:211
auto iterate_over_indices(Iteration &&iteration) const
Definition: chunked_multidim_array.h:539
auto operator[](std::size_t plain_index) -> T &
Definition: chunked_multidim_array.h:340
auto destroy_chunk_at(integral auto const chunk_index0, integral auto const ... chunk_indices) const
Definition: chunked_multidim_array.h:303
auto minmax_value() const
Definition: chunked_multidim_array.h:505
auto plain_internal_chunk_index_from_global_indices(std::size_t plain_chunk_index, integral auto const ... is) const
Definition: chunked_multidim_array.h:148
auto num_components() const
Definition: dynamic_multidim_size.h:111
auto resize(SizeRange &&size) -> void requires(is_integral< typename std::decay_t< SizeRange >::value_type >)
Definition: chunked_multidim_array.h:87
auto chunk_indices_from_global_indices(integral auto const ... is) const
Definition: chunked_multidim_array.h:204
chunked_multidim_array(SizeRange &&size, ChunkSizeRange &&chunk_size)
Definition: chunked_multidim_array.h:63
auto operator()(integral auto const ... is) -> T &
Definition: chunked_multidim_array.h:422
auto resize(std::array< Int, N > const &v)
Definition: chunked_multidim_array.h:131
auto plain_chunk_index_from_global_indices(std::index_sequence< Seq... >, integral auto const ... is) const
Definition: chunked_multidim_array.h:158
chunked_multidim_array(Reader &&reader, std::vector< std::size_t > const &chunk_size)
Definition: chunked_multidim_array.h:80
auto create_chunk_at(std::size_t const plain_chunk_index) const -> auto const &
Definition: chunked_multidim_array.h:286
std::unique_ptr< chunk_t > chunk_ptr_t
Definition: chunked_multidim_array.h:33
auto at(std::array< S, N > const &is) const -> T const &
Definition: chunked_multidim_array.h:448
auto at(integral auto const ... is) const -> T const &
Definition: chunked_multidim_array.h:362
auto at(base_tensor< Tensor, S, N > const &is) -> T &
Definition: chunked_multidim_array.h:376
Definition: invoke_unpacked.h:11