10#ifndef XTENSOR_ARRAY_HPP
11#define XTENSOR_ARRAY_HPP
16#include <xtl/xsequence.hpp>
18#include "../containers/xbuffer_adaptor.hpp"
19#include "../containers/xcontainer.hpp"
20#include "../core/xsemantic.hpp"
31 template <
class EC, layout_type L,
class SC,
class Tag>
34 template <
class EC, layout_type L,
class SC>
40 template <
class EC, layout_type L,
class SC,
class Tag>
44 template <
class EC, layout_type L,
class SC,
class Tag>
47 using storage_type = EC;
48 using reference = inner_reference_t<storage_type>;
49 using const_reference =
typename storage_type::const_reference;
50 using size_type =
typename storage_type::size_type;
51 using shape_type = SC;
52 using strides_type = get_strides_t<shape_type>;
53 using backstrides_type = get_strides_t<shape_type>;
54 using inner_shape_type = shape_type;
55 using inner_strides_type = strides_type;
56 using inner_backstrides_type = backstrides_type;
61 template <
class EC, layout_type L,
class SC,
class Tag>
80 template <
class EC, layout_type L,
class SC,
class Tag>
82 public xcontainer_semantic<xarray_container<EC, L, SC, Tag>>,
83 public extension::xarray_container_base_t<EC, L, SC, Tag>
88 using base_type = xstrided_container<self_type>;
89 using semantic_base = xcontainer_semantic<self_type>;
90 using extension_base = extension::xarray_container_base_t<EC, L, SC, Tag>;
91 using storage_type =
typename base_type::storage_type;
92 using allocator_type =
typename base_type::allocator_type;
93 using value_type =
typename base_type::value_type;
94 using reference =
typename base_type::reference;
95 using const_reference =
typename base_type::const_reference;
96 using pointer =
typename base_type::pointer;
97 using const_pointer =
typename base_type::const_pointer;
98 using shape_type =
typename base_type::shape_type;
99 using inner_shape_type =
typename base_type::inner_shape_type;
100 using strides_type =
typename base_type::strides_type;
101 using backstrides_type =
typename base_type::backstrides_type;
102 using inner_strides_type =
typename base_type::inner_strides_type;
103 using inner_backstrides_type =
typename base_type::inner_backstrides_type;
104 using temporary_type =
typename semantic_base::temporary_type;
105 using expression_tag = Tag;
106 static constexpr std::size_t rank = SIZE_MAX;
122 template <
class S = shape_type>
133 template <std::
size_t N>
135 template <std::
size_t N>
146 storage_type m_storage;
148 storage_type& storage_impl() noexcept;
149 const storage_type& storage_impl() const noexcept;
160 template <
class EC, layout_type L,
class SC,
class Tag>
163 template <
class EC, layout_type L,
class SC>
169 template <
class EC, layout_type L,
class SC,
class Tag>
173 template <
class EC, layout_type L,
class SC,
class Tag>
176 using storage_type = std::remove_reference_t<EC>;
177 using reference = inner_reference_t<storage_type>;
178 using const_reference =
typename storage_type::const_reference;
179 using size_type =
typename storage_type::size_type;
180 using shape_type = SC;
181 using strides_type = get_strides_t<shape_type>;
182 using backstrides_type = get_strides_t<shape_type>;
183 using inner_shape_type = shape_type;
184 using inner_strides_type = strides_type;
185 using inner_backstrides_type = backstrides_type;
190 template <
class EC, layout_type L,
class SC,
class Tag>
212 template <
class EC, layout_type L,
class SC,
class Tag>
213 class xarray_adaptor :
public xstrided_container<xarray_adaptor<EC, L, SC, Tag>>,
214 public xcontainer_semantic<xarray_adaptor<EC, L, SC, Tag>>,
215 public extension::xarray_adaptor_base_t<EC, L, SC, Tag>
219 using container_closure_type = EC;
222 using base_type = xstrided_container<self_type>;
223 using semantic_base = xcontainer_semantic<self_type>;
224 using extension_base = extension::xarray_adaptor_base_t<EC, L, SC, Tag>;
225 using storage_type =
typename base_type::storage_type;
226 using allocator_type =
typename base_type::allocator_type;
227 using shape_type =
typename base_type::shape_type;
228 using strides_type =
typename base_type::strides_type;
229 using backstrides_type =
typename base_type::backstrides_type;
230 using temporary_type =
typename semantic_base::temporary_type;
231 using expression_tag = Tag;
232 static constexpr std::size_t rank = SIZE_MAX;
255 template <
class P,
class S>
256 void reset_buffer(P&& pointer, S&&
size);
260 container_closure_type m_storage;
262 storage_type& storage_impl() noexcept;
263 const storage_type& storage_impl() const noexcept;
279 template <class EC,
layout_type L, class SC, class Tag>
282 , m_storage(1, value_type())
292 template <
class EC, layout_type L,
class SC,
class Tag>
306 template <
class EC, layout_type L,
class SC,
class Tag>
308 const shape_type& shape,
309 const_reference value,
315 std::fill(m_storage.begin(), m_storage.end(), value);
323 template <
class EC, layout_type L,
class SC,
class Tag>
337 template <
class EC, layout_type L,
class SC,
class Tag>
339 const shape_type& shape,
341 const_reference value
346 std::fill(m_storage.begin(), m_storage.end(), value);
354 template <
class EC, layout_type L,
class SC,
class Tag>
359 nested_copy(m_storage.begin(), t);
369 template <
class EC, layout_type L,
class SC,
class Tag>
372 inner_shape_type&& shape,
375 : base_type(std::move(shape), std::move(
strides))
376 , m_storage(std::move(
storage))
390 template <
class EC, layout_type L,
class SC,
class Tag>
396 L == tmp ? nested_copy(m_storage.begin(), t) : nested_copy(this->
template begin<tmp>(), t);
403 template <
class EC, layout_type L,
class SC,
class Tag>
409 L == tmp ? nested_copy(m_storage.begin(), t) : nested_copy(this->
template begin<tmp>(), t);
416 template <
class EC, layout_type L,
class SC,
class Tag>
422 L == tmp ? nested_copy(m_storage.begin(), t) : nested_copy(this->
template begin<tmp>(), t);
429 template <
class EC, layout_type L,
class SC,
class Tag>
435 L == tmp ? nested_copy(m_storage.begin(), t) : nested_copy(this->
template begin<tmp>(), t);
442 template <
class EC, layout_type L,
class SC,
class Tag>
448 L == tmp ? nested_copy(m_storage.begin(), t) : nested_copy(this->
template begin<tmp>(), t);
457 template <
class EC, layout_type L,
class SC,
class Tag>
461 shape_type
shape = xtl::forward_sequence<shape_type, S>(s);
462 return self_type(
shape);
465 template <
class EC, layout_type L,
class SC,
class Tag>
466 template <std::
size_t N>
469 inner_shape_type(rhs.shape().cbegin(), rhs.shape().cend()),
471 inner_backstrides_type(rhs.backstrides().cbegin(), rhs.backstrides().cend()),
472 std::move(rhs.layout())
474 , m_storage(std::move(rhs.storage()))
478 template <
class EC, layout_type L,
class SC,
class Tag>
479 template <std::
size_t N>
480 inline xarray_container<EC, L, SC, Tag>&
481 xarray_container<EC, L, SC, Tag>::operator=(xtensor_container<EC, N, L, Tag>&& rhs)
483 this->shape_impl().assign(rhs.shape().cbegin(), rhs.shape().cend());
484 this->strides_impl().assign(rhs.strides().cbegin(), rhs.strides().cend());
485 this->backstrides_impl().assign(rhs.backstrides().cbegin(), rhs.backstrides().cend());
486 this->mutable_layout() = rhs.layout();
487 m_storage = std::move(rhs.storage());
498 template <
class EC, layout_type L,
class SC,
class Tag>
507 detail::resize_data_container(m_storage, std::size_t(1));
509 semantic_base::assign(e);
515 template <
class EC, layout_type L,
class SC,
class Tag>
517 inline auto xarray_container<EC, L, SC, Tag>::operator=(
const xexpression<E>& e) -> self_type&
519 return semantic_base::operator=(e);
524 template <
class EC, layout_type L,
class SC,
class Tag>
525 inline auto xarray_container<EC, L, SC, Tag>::storage_impl() noexcept -> storage_type&
530 template <
class EC, layout_type L,
class SC,
class Tag>
531 inline auto xarray_container<EC, L, SC, Tag>::storage_impl() const noexcept -> const storage_type&
548 template <
class EC, layout_type L,
class SC,
class Tag>
551 , m_storage(std::move(
storage))
559 template <
class EC, layout_type L,
class SC,
class Tag>
573 template <
class EC, layout_type L,
class SC,
class Tag>
577 , m_storage(std::forward<D>(
storage))
589 template <
class EC, layout_type L,
class SC,
class Tag>
593 const shape_type& shape,
597 , m_storage(std::forward<D>(
storage))
604 template <
class EC, layout_type L,
class SC,
class Tag>
605 inline auto xarray_adaptor<EC, L, SC, Tag>::operator=(
const xarray_adaptor& rhs) -> self_type&
607 base_type::operator=(rhs);
608 m_storage = rhs.m_storage;
612 template <
class EC, layout_type L,
class SC,
class Tag>
613 inline auto xarray_adaptor<EC, L, SC, Tag>::operator=(xarray_adaptor&& rhs) -> self_type&
615 base_type::operator=(std::move(rhs));
616 m_storage = rhs.m_storage;
620 template <
class EC, layout_type L,
class SC,
class Tag>
621 inline auto xarray_adaptor<EC, L, SC, Tag>::operator=(
temporary_type&& rhs) -> self_type&
623 base_type::shape_impl() = std::move(
const_cast<shape_type&
>(rhs.shape()));
624 base_type::strides_impl() = std::move(
const_cast<strides_type&
>(rhs.strides()));
625 base_type::backstrides_impl() = std::move(
const_cast<backstrides_type&
>(rhs.backstrides()));
626 m_storage = std::move(rhs.storage());
637 template <
class EC, layout_type L,
class SC,
class Tag>
639 inline auto xarray_adaptor<EC, L, SC, Tag>::operator=(
const xexpression<E>& e) -> self_type&
641 return semantic_base::operator=(e);
646 template <
class EC, layout_type L,
class SC,
class Tag>
647 inline auto xarray_adaptor<EC, L, SC, Tag>::storage_impl() noexcept -> storage_type&
652 template <
class EC, layout_type L,
class SC,
class Tag>
653 inline auto xarray_adaptor<EC, L, SC, Tag>::storage_impl() const noexcept -> const storage_type&
658 template <
class EC, layout_type L,
class SC,
class Tag>
659 template <
class P,
class S>
660 inline void xarray_adaptor<EC, L, SC, Tag>::reset_buffer(P&& pointer, S&& size)
662 return m_storage.reset_data(std::forward<P>(pointer), std::forward<S>(size));
Dense multidimensional container adaptor with tensor semantic.
xarray_adaptor(D &&storage, const shape_type &shape, layout_type l=L)
Constructs an xarray_adaptor of the given stl-like container, with the specified shape and layout_typ...
xarray_adaptor(D &&storage, const shape_type &shape, const strides_type &strides)
Constructs an xarray_adaptor of the given stl-like container, with the specified shape and strides.
xarray_adaptor(const storage_type &storage)
Constructs an xarray_adaptor of the given stl-like container.
xarray_adaptor(storage_type &&storage)
Constructs an xarray_adaptor of the given stl-like container.
Dense multidimensional container with tensor semantic.
xarray_container(const shape_type &shape, const strides_type &strides, const_reference value)
Allocates an uninitialized xarray_container with the specified shape and strides.
xarray_container(const shape_type &shape, const strides_type &strides)
Allocates an uninitialized xarray_container with the specified shape and strides.
xarray_container(nested_initializer_list_t< value_type, 2 > t)
Allocates a two-dimensional xarray_container.
xarray_container(nested_initializer_list_t< value_type, 5 > t)
Allocates a five-dimensional xarray_container.
xarray_container(const shape_type &shape, layout_type l=L)
Allocates an uninitialized xarray_container with the specified shape and layout_type.
xarray_container(const shape_type &shape, const_reference value, layout_type l=L)
Allocates an xarray_container with the specified shape and layout_type.
xarray_container(const value_type &t)
Allocates an xarray_container that holds a single element initialized to the specified value.
xarray_container(nested_initializer_list_t< value_type, 1 > t)
Allocates a one-dimensional xarray_container.
xarray_container(storage_type &&storage, inner_shape_type &&shape, inner_strides_type &&strides)
Allocates an xarray_container by moving specified data, shape and strides.
xarray_container(nested_initializer_list_t< value_type, 3 > t)
Allocates a three-dimensional xarray_container.
xarray_container(nested_initializer_list_t< value_type, 4 > t)
Allocates a four-dimensional xarray_container.
xarray_container(const xexpression< E > &e)
The extended copy constructor.
xarray_container()
Allocates an uninitialized xarray_container that holds 0 element.
Base class for dense multidimensional containers.
storage_type & storage() noexcept
Returns a reference to the buffer containing the elements of the container.
size_type size() const noexcept
Returns the number of element in the container.
constexpr size_type dimension() const noexcept
Returns the number of dimensions of the container.
constexpr const inner_strides_type & strides() const noexcept
Returns the strides of the container.
constexpr const inner_shape_type & shape() const noexcept
Returns the shape of the container.
auto begin() noexcept -> select_iterator< L >
Base class for xexpressions.
derived_type & derived_cast() &noexcept
Returns a reference to the actual derived type of the xexpression.
void resize(S &&shape, bool force=false)
Dense multidimensional container with tensor semantic and fixed dimension.
auto strides(const E &e, stride_type type=stride_type::normal) noexcept
Get strides of an object.
standard mathematical functions for xexpressions