/* * This code is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This code is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this code; if not, write to the Free Software * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */ /* Copyright (C) 2022-2023 Max-Planck-Society Author: Martin Reinecke */ #ifndef DUCC0_ARRAY_DESCRIPTOR_H #define DUCC0_ARRAY_DESCRIPTOR_H #include #include "ducc0/infra/error_handling.h" #include "ducc0/infra/mav.h" #include "ducc0/bindings/typecode.h" namespace ducc0 { namespace detail_array_descriptor { using namespace std; struct ArrayDescriptor { static constexpr size_t maxdim=10; array shape; array stride; void *data; uint8_t ndim; uint8_t dtype; }; template void copy_data (const ArrayDescriptor &desc, T1 &shp, T2 &str) { auto ndim = desc.ndim; if constexpr (swapdims) for (size_t i=0; i auto prep1 (const ArrayDescriptor &desc) { static_assert(ndim<=ArrayDescriptor::maxdim, "dimensionality too high"); MR_assert(ndim==desc.ndim, "dimensionality mismatch"); MR_assert(Typecode::value==desc.dtype, "data type mismatch"); typename mav_info::shape_t shp; typename mav_info::stride_t str; copy_data(desc, shp, str); return make_tuple(shp, str); } template cmav to_cmav(const ArrayDescriptor &desc) { auto [shp, str] = prep1(desc); return cmav(reinterpret_cast(desc.data), shp, str); } template cmav to_cmav_with_typecast(const ArrayDescriptor &desc) { static_assert(sizeof(T)==sizeof(T2), "type size mismatch"); auto [shp, str] = prep1(desc); return cmav(reinterpret_cast(desc.data), shp, str); } template vmav to_vmav(ArrayDescriptor &desc) { auto [shp, str] = prep1(desc); return vmav(reinterpret_cast(desc.data), shp, str); } template auto prep2(const ArrayDescriptor &desc) { MR_assert(Typecode::value==desc.dtype, "data type mismatch"); typename fmav_info::shape_t shp(desc.ndim); typename fmav_info::stride_t str(desc.ndim); copy_data(desc, shp, str); return make_tuple(shp, str); } template cfmav to_cfmav(const ArrayDescriptor &desc) { auto [shp, str] = prep2(desc); return cfmav(reinterpret_cast(desc.data), shp, str); } template vfmav to_vfmav(ArrayDescriptor &desc) { auto [shp, str] = prep2(desc); return vfmav(reinterpret_cast(desc.data), shp, str); } template vector to_vector (const ArrayDescriptor &desc) { MR_assert(Typecode::value==desc.dtype, "data type mismatch"); MR_assert(desc.ndim==1, "need 1D array for conversion to vector"); vector res; res.reserve(desc.shape[0]); auto data = reinterpret_cast(desc.data); for (size_t i=0; i vector to_vector_subtract_1 (const ArrayDescriptor &desc) { static_assert(is_integral::value, "need an integral type for this"); MR_assert(Typecode::value==desc.dtype, "data type mismatch"); MR_assert(desc.ndim==1, "need 1D array for conversion to vector"); vector res; res.reserve(desc.shape[0]); auto data = reinterpret_cast(desc.data); for (size_t i=0; i cmav subtract_1(const cmav &inp) { vmav res(inp.shape(), UNINITIALIZED); mav_apply([](T &v1, const T &v2){v1=v2-T(1);}, 1, res, inp); return res; } } using detail_array_descriptor::ArrayDescriptor; using detail_array_descriptor::to_cmav; using detail_array_descriptor::to_cmav_with_typecast; using detail_array_descriptor::to_vmav; using detail_array_descriptor::to_cfmav; using detail_array_descriptor::to_vfmav; using detail_array_descriptor::to_vector; using detail_array_descriptor::to_vector_subtract_1; using detail_array_descriptor::subtract_1; } #endif