1 #ifndef DASH__CARTESIAN_H_ 2 #define DASH__CARTESIAN_H_ 4 #include <dash/Types.h> 5 #include <dash/Dimensional.h> 6 #include <dash/Exception.h> 7 #include <dash/internal/Logging.h> 14 #include <type_traits> 29 typedef typename std::make_signed<SizeType>::type
35 typedef IndexType index_type;
36 typedef SizeType size_type;
37 typedef std::array<SizeType, NumDimensions> extents_type;
40 template<dim_t NDim_,
typename SizeType_>
41 friend std::ostream & operator<<(
49 SizeType _rank = NumDimensions;
51 extents_type _extents = {{ }};
57 typedef std::integral_constant<dim_t, NumDimensions>
ndim;
72 template <
typename... Args>
75 _rank(NumDimensions) {
85 _rank(NumDimensions) {
96 for(
auto i = 0; i < NumDimensions; i++) {
97 if (_extents[i] != other._extents[i]) {
109 return !(*
this == other);
115 template<
typename... Args>
116 void resize(SizeType arg, Args... args) {
118 sizeof...(Args) == NumDimensions-1,
119 "Invalid number of arguments");
120 std::array<SizeType, NumDimensions>
extents =
121 {{ arg, (SizeType)(args)... }};
128 template<
typename SizeType_>
132 for(
auto i = 0; i < NumDimensions; i++ ) {
133 _extents[i] =
static_cast<SizeType
>(extents[i]);
134 _size *= _extents[i];
164 constexpr SizeType
size() const noexcept {
171 constexpr
const extents_type &
extents() const noexcept {
183 0, dim, NumDimensions-1,
184 "Dimension for CartesianSpace::extent(dim) is out of bounds");
185 return _extents[dim];
213 template <
typename... Args>
215 : parent_t(arg, args...) {
223 const ::std::array<SizeType, NumDimensions> &
extents)
224 : parent_t(extents) {
237 MemArrange Arrangement = ROW_MAJOR,
242 typedef typename std::make_unsigned<IndexType>::type
250 typedef IndexType index_type;
251 typedef SizeType size_type;
252 typedef std::array<SizeType, NumDimensions> extents_type;
254 template<dim_t NDim_>
255 friend std::ostream & operator<<(
263 SizeType _rank = NumDimensions;
265 extents_type _extents = { };
269 extents_type _offset_row_major = { };
273 extents_type _offset_col_major = { };
279 typedef std::integral_constant<dim_t, NumDimensions>
ndim;
300 template<
typename... Args>
323 if (
this == &other) {
326 for(
auto i = 0; i < NumDimensions; i++) {
327 if (_extents[i] != other._extents[i]) {
331 if (_offset_row_major[i] != other._offset_row_major[i]) {
343 return !(*
this == other);
349 template<
typename... Args>
350 void resize(SizeType arg, Args... args) {
352 sizeof...(Args) == NumDimensions-1,
353 "Invalid number of arguments");
354 std::array<SizeType, NumDimensions>
extents =
355 {{ arg, (SizeType)(args)... }};
362 template<
typename SizeType_>
366 for(
auto i = 0; i < NumDimensions; i++ ) {
367 _extents[i] =
static_cast<SizeType
>(extents[i]);
368 _size *= _extents[i];
371 _offset_row_major[NumDimensions-1] = 1;
372 for(
auto i = NumDimensions-2; i >= 0; --i) {
373 _offset_row_major[i] = _offset_row_major[i+1] * _extents[i+1];
375 _offset_col_major[0] = 1;
376 for(
auto i = 1; i < NumDimensions; ++i) {
377 _offset_col_major[i] = _offset_col_major[i-1] * _extents[i-1];
395 constexpr SizeType
size() const noexcept {
402 constexpr
const extents_type &
extents() const noexcept {
414 0, dim, NumDimensions-1,
415 "Given dimension " << dim <<
416 " for CartesianIndexSpace::extent(dim) is out of bounds");
417 return _extents[dim];
428 MemArrange AtArrangement = Arrangement>
429 constexpr IndexType
at(
430 IndexType arg, Args... args)
const {
432 sizeof...(Args) == NumDimensions-1,
433 "Invalid number of arguments");
434 return at<AtArrangement>(
435 std::array<IndexType, NumDimensions> {{
436 arg, (IndexType)(args) ... }}
447 MemArrange AtArrangement = Arrangement,
450 const std::array<OffsetType, NumDimensions> & point)
const {
452 DASH_ASSERT_GT(_size, 0,
"CartesianIndexSpace has size 0");
453 for (
auto i = 0; i < NumDimensions; i++) {
456 static_cast<IndexType>(point[i]),
457 static_cast<IndexType>(_extents[i]-1),
458 "Given coordinate for CartesianIndexSpace::at() exceeds extent");
459 SizeType offset_dim = 0;
460 if (AtArrangement == ROW_MAJOR) {
461 offset_dim = _offset_row_major[i];
462 }
else if (AtArrangement == COL_MAJOR) {
463 offset_dim = _offset_col_major[i];
465 offs += offset_dim * point[i];
480 MemArrange AtArrangement = Arrangement,
483 const std::array<OffsetType, NumDimensions> & point,
484 const ViewSpec_t & viewspec)
const {
485 std::array<OffsetType, NumDimensions> coords{};
486 for (
auto d = 0; d < NumDimensions; ++d) {
487 coords[d] = point[d] + viewspec.offset(d);
496 template<MemArrange CoordArrangement = Arrangement>
497 std::array<IndexType, NumDimensions>
coords(
498 IndexType
index)
const 500 DASH_ASSERT_GT(_size, 0,
"CartesianIndexSpace has size 0");
502 0, index, static_cast<IndexType>(_size-1),
503 "Given index for CartesianIndexSpace::coords() is out of bounds");
505 ::std::array<IndexType, NumDimensions> pos{};
506 if (CoordArrangement == ROW_MAJOR) {
507 for(
auto i = 0; i < NumDimensions; ++i) {
508 pos[i] = index / _offset_row_major[i];
509 index = index % _offset_row_major[i];
511 }
else if (CoordArrangement == COL_MAJOR) {
512 for(
auto i = NumDimensions-1; i >= 0; --i) {
513 pos[i] = index / _offset_col_major[i];
514 index = index % _offset_col_major[i];
525 template<MemArrange CoordArrangement = Arrangement>
526 std::array<IndexType, NumDimensions>
coords(
528 const ViewSpec_t & viewspec)
const 530 std::array<IndexType, NumDimensions> pos{};
532 if (CoordArrangement == ROW_MAJOR)
534 offset[NumDimensions-1] = 1;
535 for(
auto i = NumDimensions-2; i >= 0; --i)
536 offset[i] = offset[i+1] * viewspec.extent(i+1);
538 for(
auto i = 0; i < NumDimensions; ++i)
540 pos[i] = index / offset[i] + viewspec.offset(i);
541 index = index % offset[i];
544 else if (CoordArrangement == COL_MAJOR)
547 for(
auto i = 1; i < NumDimensions; ++i)
548 offset[i] = offset[i-1] * viewspec.extent(i-1);
550 for(
auto i = NumDimensions-1; i >= 0; --i)
552 pos[i] = index / offset[i] + viewspec.offset(i);
553 index = index % offset[i];
564 template<MemArrange CoordArrangement = Arrangement>
568 IndexType dim_offset)
const {
571 return (index >= 0 && index < this->
size());
573 auto base_offset = 0;
574 if (CoordArrangement == COL_MAJOR) {
575 base_offset = _offset_col_major[dimension];
576 }
else if (CoordArrangement == ROW_MAJOR) {
577 base_offset = _offset_row_major[dimension];
579 for (
auto d = 0; d < NumDimensions; ++d) {
589 template<dim_t U = NumDimensions>
590 constexpr
typename std::enable_if< (U > 0), SizeType >::type
591 x(SizeType offs)
const {
592 return coords(offs)[0];
598 template<dim_t U = NumDimensions>
599 constexpr
typename std::enable_if< (U > 1), SizeType >::type
600 y(SizeType offs)
const {
601 return coords(offs)[1];
607 template<dim_t U = NumDimensions>
608 constexpr
typename std::enable_if< (U > 2), SizeType >::type
609 z(SizeType offs)
const {
610 return coords(offs)[2];
624 size_t NumDimensions,
625 MemArrange Arrangement = ROW_MAJOR,
631 typedef typename std::make_unsigned<IndexType>::type
647 : parent_t(sizespec),
648 _distspec(distspec) {
657 : parent_t(
SizeSpec<NumDimensions>()),
658 _distspec(distspec) {
665 if (!(parent_t::operator==(other))) {
668 return _distspec == other._distspec;
675 return !(*
this == other);
681 template<
typename... Args>
682 void resize(SizeType arg, Args... args) {
684 sizeof...(Args) == NumDimensions-1,
685 "Invalid number of arguments");
686 std::array<SizeType, NumDimensions>
extents =
687 {{ arg, (SizeType)(args)... }};
694 template<
typename SizeType_>
696 if (!_distspec.is_tiled()) {
697 parent_t::resize(extents);
702 "CartesianIndexSpace::resize(IndexType) not implemented for tiles!");
713 MemArrange AtArrangement = Arrangement>
714 constexpr IndexType
at(
715 IndexType arg, Args... args)
const {
717 sizeof...(Args) == NumDimensions-1,
718 "Invalid number of arguments");
719 return at<AtArrangement>(
720 std::array<IndexType, NumDimensions> {
721 arg, (IndexType)(args) ... }
732 MemArrange AtArrangement = Arrangement,
735 const std::array<OffsetType, NumDimensions> & point)
const {
736 if (!_distspec.is_tiled()) {
738 return parent_t::at(point);
743 "CartesianIndexSpace::at(IndexType) not implemented for tiles!");
756 MemArrange AtArrangement = Arrangement,
759 const std::array<OffsetType, NumDimensions> & point,
760 const ViewSpec_t & viewspec)
const {
761 std::array<OffsetType, NumDimensions> coords;
762 for (
auto d = 0; d < NumDimensions; ++d) {
763 coords[d] = point[d] + viewspec[d].offset;
772 template<MemArrange CoordArrangement = Arrangement>
773 std::array<IndexType, NumDimensions>
coords(IndexType index)
const {
774 if (!_distspec.is_tiled()) {
776 return parent_t::coords(index);
781 "CartesianIndexSpace::coords(IndexType) not implemented for tiles!");
791 std::ostream & operator<<(
795 std::ostringstream ss;
799 for (
auto dim = 0; dim < NumDimensions; ++dim) {
803 ss << cartesian_space.
extents()[dim];
806 return operator<<(os, ss.str());
811 std::ostream & operator<<(
815 std::ostringstream ss;
819 for (
auto dim = 0; dim < NumDimensions; ++dim) {
823 ss << cartesian_space.
extents()[dim];
826 return operator<<(os, ss.str());
831 #endif // DASH__CARTESIAN_H_ constexpr LocalMemoryLayout(const SizeSpec< NumDimensions > &sizespec, const DistributionSpec< NumDimensions > &distspec)
Constructor, creates an instance of LocalMemoryLayout from a SizeSpec and a DistributionSpec of NumDi...
internal::default_unsigned_index default_size_t
Unsigned integer type used as default for size values.
constexpr bool operator!=(const self_t &other) const
Inequality comparison operator.
constexpr std::enable_if< std::is_integral< IndexType >::value, IndexType >::type index(IndexType idx)
IndexType at(const std::array< OffsetType, NumDimensions > &point) const
Convert the given cartesian point to its respective linear index.
CartesianIndexSpace(const extents_type &extents)
Constructor, creates a cartesian index space of given extents.
This class is a simple memory pool which holds allocates elements of size ValueType.
constexpr dim_t rank() const noexcept
The number of dimension in the cartesian space with extent greater than 1.
CartesianSpace(const extents_type &extents)
Constructor, creates a cartesian space of given extents.
Specifies cartesian extents in a specific number of dimensions.
Specifies view parameters for implementing submat, rows and cols.
CartesianSpace(SizeType arg, Args... args)
Constructor, creates a cartesian index space of given extents in all dimensions.
bool operator==(const self_t &other) const
Equality comparison operator.
int dim_t
Scalar type for a dimension value, with 0 indicating the first dimension.
std::integral_constant< dim_t, NumDimensions > ndim
The number of dimension in the cartesian space.
Specifies how local element indices are arranged in a specific number of dimensions.
void resize(const std::array< SizeType_, NumDimensions > &extents)
Change the extent of the cartesian space in every dimension.
IndexType at(const std::array< OffsetType, NumDimensions > &point) const
Convert the given cartesian point to its respective linear index.
constexpr dim_t rank() const noexcept
The number of dimension in the cartesian space with extent greater than 1.
constexpr SizeSpec()
Default constructor, creates a space of extent 0 in all dimensions.
Cartesian space defined by extents in n dimensions.
CartesianIndexSpace(SizeType arg, Args... args)
Constructor, creates a cartesian index space of given extents.
void resize(SizeType arg, Args... args)
Change the extent of the cartesian space in every dimension.
constexpr LocalMemoryLayout(const DistributionSpec< NumDimensions > &distspec)
Constructor, creates an instance of LocalMemoryLayout with initial extents 0 and a DistributionSpec o...
internal::default_signed_index default_index_t
Signed integer type used as default for index values.
constexpr bool operator!=(const self_t &other) const
Inequality comparison operator.
constexpr SizeSpec(const ::std::array< SizeType, NumDimensions > &extents)
Constructor, creates a cartesian index space of given extents in all dimensions.
constexpr const extents_type & extents() const noexcept
Extents of the cartesian space, by dimension.
std::array< IndexType, NumDimensions > coords(IndexType index) const
Convert given linear offset (index) to cartesian coordinates.
std::integral_constant< dim_t, NumDimensions > ndim
The number of dimension in the cartesian space.
constexpr CartesianSpace()
Default constructor, creates a cartesian space of extent 0 in all dimensions.
SizeType extent(dim_t dim) const
The extent of the cartesian space in the given dimension.
constexpr bool operator!=(const self_t &other) const
Inequality comparison operator.
Defines a cartesian, totally-ordered index space by mapping linear indices to cartesian coordinates d...
constexpr IndexType at(IndexType arg, Args... args) const
Convert the given coordinates to their respective linear index.
constexpr std::enable_if<(U > 2), SizeType >::type z(SizeType offs) const
Accessor for dimension 3 (z), enabled for dimensionality > 2.
constexpr SizeSpec(SizeType arg, Args... args)
Constructor, creates a cartesian space of given extents.
void resize(dim_t dim, SizeType extent)
Change the extent of the cartesian space in the given dimension.
void resize(SizeType arg, Args... args)
Change the extent of the cartesian space in every dimension.
bool operator==(const self_t &other) const
Equality comparison operator.
SizeType extent(dim_t dim) const
The extent of the cartesian space in the given dimension.
std::string typestr(const T &obj)
Returns string containing the type name of the given object.
constexpr std::enable_if<(U > 0), SizeType >::type x(SizeType offs) const
Accessor for dimension 1 (x), enabled for dimensionality > 0.
bool operator==(const self_t &other) const
Equality comparison operator.
void resize(std::array< SizeType_, NumDimensions > extents)
Change the extent of the cartesian space in every dimension.
IndexType at(const std::array< OffsetType, NumDimensions > &point, const ViewSpec_t &viewspec) const
Convert the given cartesian point to a linear index, respective to the offsets specified in the given...
constexpr std::enable_if<(U > 1), SizeType >::type y(SizeType offs) const
Accessor for dimension 2 (y), enabled for dimensionality > 1.
constexpr SizeType size() const noexcept
The number of discrete elements within the space spanned by the coordinate.
void resize(dim_t dim, SizeType extent)
Change the extent of the cartesian space in the given dimension.
void resize(const std::array< SizeType_, NumDimensions > &extents)
Change the extent of the cartesian space in every dimension.
constexpr SizeType size() const noexcept
The number of discrete elements within the space spanned by the coordinate.
void resize(SizeType arg, Args... args)
Change the extent of the cartesian space in every dimension.
constexpr IndexType at(IndexType arg, Args... args) const
Convert the given coordinates to their respective linear index.
constexpr const extents_type & extents() const noexcept
Extents of the cartesian space, by dimension.
std::array< IndexType, NumDimensions > coords(IndexType index) const
Convert given linear offset (index) to cartesian coordinates.
DistributionSpec describes distribution patterns of all dimensions,.
IndexType at(const std::array< OffsetType, NumDimensions > &point, const ViewSpec_t &viewspec) const
Convert the given cartesian point to a linear index, respective to the offsets specified in the given...
std::array< IndexType, NumDimensions > coords(IndexType index, const ViewSpec_t &viewspec) const
Convert given linear offset (index) to cartesian coordinates with respect to a given viewspec...