From f5a0ec1bba3fb1773a065ecfa0b2272aaa45ddd7 Mon Sep 17 00:00:00 2001 From: Victoriya Fedotova Date: Wed, 4 Dec 2024 04:19:39 -0800 Subject: [PATCH 1/5] Initial version of documentations for data management primitives --- docs/doxygen/oneapi/Doxyfile | 23 ++++++++++- .../data-management/backend-primitives.rst | 39 +++++++++++++++++++ .../api/data-management/backend/ndarray.rst | 33 ++++++++++++++++ docs/source/api/data-management/index.rst | 3 +- docs/source/conf.py | 5 ++- docs/source/contribution/cpu_features.rst | 8 ++-- .../abc-classification-train-kernel.rst | 0 ...c-classification-train-method1-fpt-cpu.rst | 0 .../abc-classification-train-method1-impl.rst | 0 .../abc-classification-train-method2-impl.rst | 0 .../data-management/backend-primitives.rst | 25 ++++++++++++ docs/source/onedal/data-management/index.rst | 1 + 12 files changed, 129 insertions(+), 8 deletions(-) create mode 100644 docs/source/api/data-management/backend-primitives.rst create mode 100644 docs/source/api/data-management/backend/ndarray.rst rename docs/source/includes/{cpu_features => cpu-features}/abc-classification-train-kernel.rst (100%) rename docs/source/includes/{cpu_features => cpu-features}/abc-classification-train-method1-fpt-cpu.rst (100%) rename docs/source/includes/{cpu_features => cpu-features}/abc-classification-train-method1-impl.rst (100%) rename docs/source/includes/{cpu_features => cpu-features}/abc-classification-train-method2-impl.rst (100%) create mode 100644 docs/source/onedal/data-management/backend-primitives.rst diff --git a/docs/doxygen/oneapi/Doxyfile b/docs/doxygen/oneapi/Doxyfile index 93dd88f6320..8be3ceb3fa8 100644 --- a/docs/doxygen/oneapi/Doxyfile +++ b/docs/doxygen/oneapi/Doxyfile @@ -902,8 +902,27 @@ EXCLUDE_SYMLINKS = NO # Note that the wildcards are matched against the file with absolute path, so to # exclude all test directories for example use the pattern */test/* -EXCLUDE_PATTERNS = */backend/* \ - */detail/* +EXCLUDE_PATTERNS = */backend/interop/* \ + */backend/primitives/blas/* \ + */backend/primitives/distance/* \ + */backend/primitives/heap/* \ + */backend/primitives/intersection/* \ + */backend/primitives/lapack/* \ + */backend/primitives/objective_function/* \ + */backend/primitives/optimizers/* \ + */backend/primitives/placement/* \ + */backend/primitives/reduction/* \ + */backend/primitives/regression/* \ + */backend/primitives/rng/* \ + */backend/primitives/search/* \ + */backend/primitives/selection/* \ + */backend/primitives/sort/* \ + */backend/primitives/sparse_blas/* \ + */backend/primitives/stat/* \ + */backend/primitives/test/* \ + */backend/primitives/voting/* \ + */detail/* \ + */table/backend/* # The EXCLUDE_SYMBOLS tag can be used to specify one or more symbol names diff --git a/docs/source/api/data-management/backend-primitives.rst b/docs/source/api/data-management/backend-primitives.rst new file mode 100644 index 00000000000..fccc2cddee5 --- /dev/null +++ b/docs/source/api/data-management/backend-primitives.rst @@ -0,0 +1,39 @@ +.. ****************************************************************************** +.. * Copyright contributors to the oneDAL project +.. * +.. * Licensed under the Apache License, Version 2.0 (the "License"); +.. * you may not use this file except in compliance with the License. +.. * You may obtain a copy of the License at +.. * +.. * http://www.apache.org/licenses/LICENSE-2.0 +.. * +.. * Unless required by applicable law or agreed to in writing, software +.. * distributed under the License is distributed on an "AS IS" BASIS, +.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. * See the License for the specific language governing permissions and +.. * limitations under the License. +.. *******************************************************************************/ + +.. highlight:: cpp + + .. _api_dm_backend_primitives: + +================== +Backend Primitives +================== + +Refer to :ref:`Developer Guide: Backend Primitives `. + +.. _backend_primitives_programming_interface: + +--------------------- +Programming interface +--------------------- + +All types and functions in this section are declared in the +``oneapi::dal::backend::primitives`` namespace and be available via inclusion of the +``oneapi/dal/backend/primitives/ndarray.hpp`` header file. + +.. toctree:: + + backend/ndarray.rst diff --git a/docs/source/api/data-management/backend/ndarray.rst b/docs/source/api/data-management/backend/ndarray.rst new file mode 100644 index 00000000000..3fc1c794fcb --- /dev/null +++ b/docs/source/api/data-management/backend/ndarray.rst @@ -0,0 +1,33 @@ +.. ****************************************************************************** +.. * Copyright contributors to the oneDAL project +.. * +.. * Licensed under the Apache License, Version 2.0 (the "License"); +.. * you may not use this file except in compliance with the License. +.. * You may obtain a copy of the License at +.. * +.. * http://www.apache.org/licenses/LICENSE-2.0 +.. * +.. * Unless required by applicable law or agreed to in writing, software +.. * distributed under the License is distributed on an "AS IS" BASIS, +.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. * See the License for the specific language governing permissions and +.. * limitations under the License. +.. *******************************************************************************/ + +.. _api_ndarray: + +====================== +Multidimensional array +====================== + +The ``ndarray`` class provides ... + +--------------------- +Programming interface +--------------------- + +All types and functions in this section are declared in the +``oneapi::dal::backend::primitives`` namespace and be available via inclusion of the +``oneapi/dal/table/ndarray.hpp`` header file. + +.. onedal_class:: oneapi::dal::backend::primitives::ndarray diff --git a/docs/source/api/data-management/index.rst b/docs/source/api/data-management/index.rst index 7d0513057fb..ffe7b568e87 100644 --- a/docs/source/api/data-management/index.rst +++ b/docs/source/api/data-management/index.rst @@ -27,4 +27,5 @@ Refer to :ref:`Developer Guide: Data Management `. data-sources.rst graphs.rst graph-service.rst - tables.rst \ No newline at end of file + tables.rst + backend-primitives.rst \ No newline at end of file diff --git a/docs/source/conf.py b/docs/source/conf.py index 7638f138fc2..58dc2f22490 100644 --- a/docs/source/conf.py +++ b/docs/source/conf.py @@ -392,5 +392,8 @@ ('cpp:identifier', 'kind::induced'), ('cpp:identifier', 'kind::non_induced'), ('cpp:identifier', 'preview'), - ('cpp:identifier', 'connected_components') + ('cpp:identifier', 'connected_components'), + + # backend primitives - data management + ('cpp:identifier', 'ndarray') ] diff --git a/docs/source/contribution/cpu_features.rst b/docs/source/contribution/cpu_features.rst index e328bb80f47..adb719a3de3 100644 --- a/docs/source/contribution/cpu_features.rst +++ b/docs/source/contribution/cpu_features.rst @@ -159,7 +159,7 @@ These files contain the definitions of one or several template classes that defi do the actual computations. Here is a variant of the ``Abc`` training algorithm kernel definition in the file `abc_classification_train_kernel.h`: -.. include:: ../includes/cpu_features/abc-classification-train-kernel.rst +.. include:: ../includes/cpu-features/abc-classification-train-kernel.rst Typical template parameters are: @@ -178,7 +178,7 @@ These files contain the implementations of the computational functions defined i Here is a variant of ``method1`` implementation for ``Abc`` training algorithm that does not contain any instruction set specific code. The implementation is located in the file `abc_classification_train_method1_impl.i`: -.. include:: ../includes/cpu_features/abc-classification-train-method1-impl.rst +.. include:: ../includes/cpu-features/abc-classification-train-method1-impl.rst Although the implementation of the ``method1`` does not contain any instruction set specific code, it is expected that the developers leverage SIMD related macros available in |short_name|. @@ -195,7 +195,7 @@ For example, the AVX-512 specific code should be gated on the value ``__CPUID__( Then the implementation of the ``method2`` in the file `abc_classification_train_method2_impl.i` will look like: -.. include:: ../includes/cpu_features/abc-classification-train-method2-impl.rst +.. include:: ../includes/cpu-features/abc-classification-train-method2-impl.rst \*_fpt_cpu.cpp -------------- @@ -205,7 +205,7 @@ These files contain the instantiations of the template classes defined in the fi The instantiation of the ``Abc`` training algorithm kernel for ``method1`` is located in the file `abc_classification_train_method1_batch_fpt_cpu.cpp`: -.. include:: ../includes/cpu_features/abc-classification-train-method1-fpt-cpu.rst +.. include:: ../includes/cpu-features/abc-classification-train-method1-fpt-cpu.rst `_fpt_cpu.cpp` files are not compiled directly into object files. First, multiple copies of those files are made replacing the ``fpt``, which stands for 'floating point type', and ``cpu`` parts of the file name diff --git a/docs/source/includes/cpu_features/abc-classification-train-kernel.rst b/docs/source/includes/cpu-features/abc-classification-train-kernel.rst similarity index 100% rename from docs/source/includes/cpu_features/abc-classification-train-kernel.rst rename to docs/source/includes/cpu-features/abc-classification-train-kernel.rst diff --git a/docs/source/includes/cpu_features/abc-classification-train-method1-fpt-cpu.rst b/docs/source/includes/cpu-features/abc-classification-train-method1-fpt-cpu.rst similarity index 100% rename from docs/source/includes/cpu_features/abc-classification-train-method1-fpt-cpu.rst rename to docs/source/includes/cpu-features/abc-classification-train-method1-fpt-cpu.rst diff --git a/docs/source/includes/cpu_features/abc-classification-train-method1-impl.rst b/docs/source/includes/cpu-features/abc-classification-train-method1-impl.rst similarity index 100% rename from docs/source/includes/cpu_features/abc-classification-train-method1-impl.rst rename to docs/source/includes/cpu-features/abc-classification-train-method1-impl.rst diff --git a/docs/source/includes/cpu_features/abc-classification-train-method2-impl.rst b/docs/source/includes/cpu-features/abc-classification-train-method2-impl.rst similarity index 100% rename from docs/source/includes/cpu_features/abc-classification-train-method2-impl.rst rename to docs/source/includes/cpu-features/abc-classification-train-method2-impl.rst diff --git a/docs/source/onedal/data-management/backend-primitives.rst b/docs/source/onedal/data-management/backend-primitives.rst new file mode 100644 index 00000000000..ab563bbc280 --- /dev/null +++ b/docs/source/onedal/data-management/backend-primitives.rst @@ -0,0 +1,25 @@ +.. ****************************************************************************** +.. * Copyright contributors to the oneDAL project +.. * +.. * Licensed under the Apache License, Version 2.0 (the "License"); +.. * you may not use this file except in compliance with the License. +.. * You may obtain a copy of the License at +.. * +.. * http://www.apache.org/licenses/LICENSE-2.0 +.. * +.. * Unless required by applicable law or agreed to in writing, software +.. * distributed under the License is distributed on an "AS IS" BASIS, +.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. * See the License for the specific language governing permissions and +.. * limitations under the License. +.. *******************************************************************************/ + +.. highlight:: cpp + +.. _dm_backend_primitives: + +================== +Backend Primitives +================== + +This section describes the types related to internal backend data management primitives. \ No newline at end of file diff --git a/docs/source/onedal/data-management/index.rst b/docs/source/onedal/data-management/index.rst index aabd23a0a6a..92e2347b627 100644 --- a/docs/source/onedal/data-management/index.rst +++ b/docs/source/onedal/data-management/index.rst @@ -291,3 +291,4 @@ This section includes the detailed descriptions of all data management objects i data-sources.rst graphs.rst tables.rst + backend-primitives.rst From f87e7db8be2d339e6f5f15c423035489be37aa29 Mon Sep 17 00:00:00 2001 From: Victoriya Fedotova Date: Thu, 5 Dec 2024 05:48:06 -0800 Subject: [PATCH 2/5] Add API reference for ndarray --- cpp/oneapi/dal/backend/primitives/ndarray.hpp | 109 ++++++++++++++++-- docs/doxygen/oneapi/Doxyfile | 2 +- docs/source/conf.py | 13 ++- 3 files changed, 114 insertions(+), 10 deletions(-) diff --git a/cpp/oneapi/dal/backend/primitives/ndarray.hpp b/cpp/oneapi/dal/backend/primitives/ndarray.hpp index 4875da93713..d38dcb91e8b 100644 --- a/cpp/oneapi/dal/backend/primitives/ndarray.hpp +++ b/cpp/oneapi/dal/backend/primitives/ndarray.hpp @@ -539,14 +539,26 @@ inline sycl::event fill(sycl::queue& q, } #endif +/// Multidimensional array +/// +/// @tparam T The type of the memory block elements within the multidimensional array. +/// :literal:`T` can represent :expr:`float`, :expr:`double` or :expr:`std::int32_t`. +/// @tparam axis_count The number of dimensions in the multidimensional array. +/// @tparam order Row-major or column-major order of the 2-dimensional array. template class ndarray : public ndview { template friend class ndarray; using base = ndview; + + /// Type of the object holding the multidimensional array shape using shape_t = ndshape; + + /// Type of a shared pointer to :literal:`T` using shared_t = dal::detail::shared; + + /// Type of the array with elements of type :literal:`T` using array_t = dal::array>; struct array_deleter { @@ -562,54 +574,110 @@ class ndarray : public ndview { public: ndarray() = default; + /// Creates a new multidimensional array instance by passing the pointer to externally-defined memory block + /// for mutable data. + /// + /// @tparam Deleter The type of a deleter called on ``data`` when + /// the last ndarray that refers it is out of the scope. + /// + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. + /// @param deleter The deleter that is called on the ``data`` when the last ndarray that refers it + /// is out of the scope. template > static ndarray wrap(T* data, const shape_t& shape, Deleter&& deleter = Deleter{}) { auto shared = shared_t{ data, std::forward(deleter) }; return wrap(std::move(shared), shape); } + /// Creates a new multidimensional array instance by passing the pointer to externally-defined memory block + /// for immutable data. + /// + /// @tparam Deleter The type of a deleter called on ``data`` when + /// the last ndarray that refers it is out of the scope. + /// + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. + /// @param deleter The deleter that is called on the ``data`` when the last ndarray that refers it + /// is out of the scope. template > static ndarray wrap(const T* data, const shape_t& shape, Deleter&& deleter = Deleter{}) { auto shared = shared_t{ const_cast(data), std::forward(deleter) }; return wrap(std::move(shared), shape).set_mutability(false); } + /// Creates a new multidimensional array instance by passing the shared pointer to externally-defined + /// memory block for mutable data. + /// + /// @param data The shared pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. static ndarray wrap(const shared_t& data, const shape_t& shape) { return ndarray{ data, shape }; } + /// Creates a new multidimensional array instance by moving a shared pointer + /// to externally-defined memory block for mutable data. + /// + /// @param data R-value reference to the shared pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. static ndarray wrap(shared_t&& data, const shape_t& shape) { return ndarray{ std::move(data), shape }; } + /// Creates a new multidimensional array instance from an immutable array. + /// The created multidimensional array shares data ownership with the given array. + /// + /// @param ary The array that stores a homogeneous data block. + /// @param shape The shape of the created multidimensional array. static ndarray wrap(const array_t& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); return wrap(ary.get_data(), shape, array_deleter{ ary }); } + /// Creates a new multidimensional array instance by moving an immutable input array. + /// + /// @param ary The r-value reference to array that stores a homogeneous data block. + /// @param shape The shape of the created multidimensional array. static ndarray wrap(array_t&& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); const T* data_ptr = ary.get_data(); return wrap(data_ptr, shape, array_deleter{ std::move(ary) }); } + /// Creates a 1d ndarray instance from an immutable array. + /// The created ndarray shares data ownership with the given array. + /// + /// @param ary The array that stores a homogeneous data block. static ndarray wrap(const array_t& ary) { static_assert(axis_count == 1); return wrap(ary, shape_t{ ary.get_count() }); } + /// Creates a 1d ndarray instance by moving an immutable input array. + /// The created ndarray shares data ownership with the given array. + /// + /// @param ary The r-value reference to array that stores a homogeneous data block. static ndarray wrap(array_t&& ary) { static_assert(axis_count == 1); std::int64_t ary_count = ary.get_count(); return wrap(std::move(ary), shape_t{ ary_count }); } + /// Creates a new multidimensional array instance from a mutable array. + /// The created multidimensional array shares data ownership with the given array. + /// + /// @param ary The array that stores a homogeneous data block. + /// @param shape The shape of the created multidimensional array. static ndarray wrap_mutable(const array_t& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); auto shared = shared_t{ ary.get_mutable_data(), array_deleter{ ary } }; return wrap(std::move(shared), shape); } + /// Creates a new multidimensional array instance by moving a mutable input array. + /// + /// @param ary The r-value reference to array that stores a homogeneous data block. + /// @param shape The shape of the created multidimensional array. static ndarray wrap_mutable(array_t&& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); T* data_ptr = ary.get_mutable_data(); @@ -617,17 +685,28 @@ class ndarray : public ndview { return wrap(std::move(shared), shape); } + /// Creates a 1d ndarray instance from a mutable array. + /// The created ndarray shares data ownership with the given array. + /// + /// @param ary The array that stores a homogeneous data block. static ndarray wrap_mutable(const array_t& ary) { static_assert(axis_count == 1); return wrap_mutable(ary, shape_t{ ary.get_count() }); } + /// Creates a 1d ndarray instance by moving a mutable input array. + /// The created ndarray shares data ownership with the given array. + /// + /// @param shape The shape of the created multidimensional array. static ndarray wrap_mutable(array_t&& ary) { static_assert(axis_count == 1); std::int64_t ary_count = ary.get_count(); return wrap_mutable(std::move(ary), shape_t{ ary_count }); } + /// Creates an uninitialized multidimensional array of a requested shape. + /// + /// @param ary The r-value reference to array that stores a homogeneous data block. static ndarray empty(const shape_t& shape) { T* ptr = dal::detail::malloc(dal::detail::default_host_policy{}, shape.get_count()); return wrap(ptr, @@ -635,12 +714,20 @@ class ndarray : public ndview { dal::detail::make_default_delete(dal::detail::default_host_policy{})); } + /// Creates a multidimensional array of the requested shape and copies the values + /// from the input pointer to a memory block into that multidimensional array. + /// + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. static ndarray copy(const T* data, const shape_t& shape) { auto ary = empty(shape); ary.assign(data, shape.get_count()); return ary; } + /// Creates a multidimensional array of the requested shape and fills it with zeros. + /// + /// @param shape The shape of the created multidimensional array. static ndarray zeros(const shape_t& shape) { auto ary = empty(shape); ary.fill(T(0)); @@ -648,15 +735,27 @@ class ndarray : public ndview { } #ifdef ONEDAL_DATA_PARALLEL + /// Creates an uninitialized multidimensional array of a requested shape + /// with the elements stored in SYCL* USM. + /// + /// @param q The SYCL* queue object. + /// @param shape The shape of the created multidimensional array. + /// @param alloc_kind The kind of USM to be allocated. static ndarray empty(const sycl::queue& q, const shape_t& shape, const sycl::usm::alloc& alloc_kind = sycl::usm::alloc::shared) { T* ptr = malloc(q, shape.get_count(), alloc_kind); return wrap(ptr, shape, usm_deleter{ q }); } -#endif -#ifdef ONEDAL_DATA_PARALLEL + /// Creates a multidimensional array of the requested shape with the elements + /// stored in SYCL* USM and copies the values from the input pointer to a memory block + /// into that multidimensional array. + /// + /// @param q The SYCL* queue object. + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. + /// @param alloc_kind The kind of USM to be allocated. static std::tuple copy( sycl::queue& q, const T* data, @@ -666,9 +765,7 @@ class ndarray : public ndview { auto event = ary.assign(q, data, shape.get_count()); return { ary, event }; } -#endif -#ifdef ONEDAL_DATA_PARALLEL static std::tuple full( sycl::queue& q, const shape_t& shape, @@ -679,18 +776,14 @@ class ndarray : public ndview { auto event = ary.fill(q, value, deps); return { ary, event }; } -#endif -#ifdef ONEDAL_DATA_PARALLEL static std::tuple zeros( sycl::queue& q, const shape_t& shape, const sycl::usm::alloc& alloc_kind = sycl::usm::alloc::shared) { return full(q, shape, T(0), alloc_kind); } -#endif -#ifdef ONEDAL_DATA_PARALLEL static std::tuple ones( sycl::queue& q, const shape_t& shape, diff --git a/docs/doxygen/oneapi/Doxyfile b/docs/doxygen/oneapi/Doxyfile index 8be3ceb3fa8..cc1256afd99 100644 --- a/docs/doxygen/oneapi/Doxyfile +++ b/docs/doxygen/oneapi/Doxyfile @@ -2205,7 +2205,7 @@ INCLUDE_FILE_PATTERNS = # recursively expanded use the := operator instead of the = operator. # This tag requires that the tag ENABLE_PREPROCESSING is set to YES. -PREDEFINED = +PREDEFINED = ONEDAL_DATA_PARALLEL # If the MACRO_EXPANSION and EXPAND_ONLY_PREDEF tags are set to YES then this # tag can be used to specify a list of macro names that should be expanded. The diff --git a/docs/source/conf.py b/docs/source/conf.py index 58dc2f22490..0f14b6a35d1 100644 --- a/docs/source/conf.py +++ b/docs/source/conf.py @@ -139,6 +139,7 @@ ('cpp:identifier', 'task::by_default'), ('cpp:identifier', 'Task'), # detail + ('cpp:identifier', 'dal::detail'), ('cpp:identifier', 'detail'), ('cpp:identifier', 'detail::descriptor_base<>'), ('cpp:identifier', 'detail::descriptor_base<>::float_t'), @@ -394,6 +395,16 @@ ('cpp:identifier', 'preview'), ('cpp:identifier', 'connected_components'), + # sycl + ('cpp:identifier', 'sycl'), + ('cpp:identifier', 'sycl::queue'), + ('cpp:identifier', 'sycl::usm'), + # backend primitives - data management - ('cpp:identifier', 'ndarray') + ('cpp:identifier', 'array_t'), + ('cpp:identifier', 'ndarray'), + ('cpp:identifier', 'ndorder'), + ('cpp:identifier', 'ndshape'), + ('cpp:identifier', 'shape_t'), + ('cpp:identifier', 'shared_t') ] From 8b07f58eadd446b42c97afe3952a346c59780ed6 Mon Sep 17 00:00:00 2001 From: Victoriya Fedotova Date: Mon, 16 Dec 2024 03:12:15 -0800 Subject: [PATCH 3/5] Add comments in ndview and ndarray classes --- cpp/oneapi/dal/backend/primitives/ndarray.hpp | 359 +++++++++++++++++- docs/source/conf.py | 2 + 2 files changed, 353 insertions(+), 8 deletions(-) diff --git a/cpp/oneapi/dal/backend/primitives/ndarray.hpp b/cpp/oneapi/dal/backend/primitives/ndarray.hpp index d38dcb91e8b..6681b23d2fd 100644 --- a/cpp/oneapi/dal/backend/primitives/ndarray.hpp +++ b/cpp/oneapi/dal/backend/primitives/ndarray.hpp @@ -168,6 +168,14 @@ class ndarray_base : public base { template class ndarray; +/// The class represents a multi-dimensional view of an externally-defined memory block +/// with a fixed number of dimensions. +/// The view does not own the memory block and does not perform any memory management. +/// +/// @tparam T The type of elements in the view. +/// @tparam axis_count The number of dimensions in the view. +/// @tparam order C-contiguous (row-major) or FORTRAN-contiguous (column-major) order +/// of the elements in 2-dimensional view. template class ndview : public ndarray_base { static_assert(!std::is_const_v, "T must be non-const"); @@ -184,62 +192,128 @@ class ndview : public ndarray_base { ndview() : data_(nullptr) {} + /// Creates a new multidimensional view instance by passing the pointer to externally-defined memory block + /// for mutable data. + /// + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional view instance. static ndview wrap(T* data, const shape_t& shape) { return ndview{ data, shape }; } + /// Creates a new multidimensional view instance by passing the pointer to externally-defined memory block + /// for immutable data. + /// + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional view instance. static ndview wrap(const T* data, const shape_t& shape) { return ndview{ data, shape }; } + /// Creates a new strided multidimensional view instance by passing the pointer to externally-defined + /// memory block for mutable data. + /// + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional view. + /// @param strides The strides of the created multidimensional view. + /// + /// @return The new multidimensional view instance. static ndview wrap(T* data, const shape_t& shape, const shape_t& strides) { return ndview{ data, shape, strides }; } + /// Creates a new strided multidimensional view instance by passing the pointer to externally-defined + /// memory block for immutable data. + /// + /// @param data The pointer to a homogeneous data block. + /// @param shape The shape of the created multidimensional view. + /// @param strides The strides of the created multidimensional view. + /// + /// @return The new multidimensional view instance. static ndview wrap(const T* data, const shape_t& shape, const shape_t& strides) { return ndview{ data, shape, strides }; } + /// Creates a new multidimensional view instance from a mutable array. + /// + /// @param data The array that stores a homogeneous data block. + /// @param shape The shape of the created multidimensional view. + /// + /// @return The new multidimensional view instance. static ndview wrap_mutable(const array& data, const shape_t& shape) { ONEDAL_ASSERT(data.has_mutable_data()); ONEDAL_ASSERT(data.get_count() >= shape.get_count()); return wrap(data.get_mutable_data(), shape); } + /// Creates a new strided multidimensional view instance from a mutable array. + /// + /// @param data The array that stores a homogeneous data block. + /// @param shape The shape of the created multidimensional view. + /// @param strides The strides of the created multidimensional view. + /// + /// @return The new multidimensional view instance. static ndview wrap_mutable(const array& data, const shape_t& shape, const shape_t& strides) { ONEDAL_ASSERT(data.has_mutable_data()); ONEDAL_ASSERT(data.get_count() >= shape.get_count()); return wrap(data.get_mutable_data(), shape, strides); } + /// Creates a new 1d view instance from an immutable array. + /// + /// @param data The array that stores a homogeneous data block. + /// + /// @return The new 1d view instance. template > static ndview wrap(const array& data) { return wrap(data.get_data(), { data.get_count() }); } + /// Creates a new 1d view instance from a mutable array. + /// + /// @param data The array that stores a homogeneous data block. + /// + /// @return The new 1d view instance. template > static ndview wrap_mutable(const array& data) { ONEDAL_ASSERT(data.has_mutable_data()); return wrap(data.get_mutable_data(), { data.get_count() }); } + /// The pointer to the memory block holding immutable data. const T* get_data() const { return data_; } + /// The pointer to the memory block holding mutable data. T* get_mutable_data() const { ONEDAL_ASSERT(data_is_mutable_); return const_cast(data_); } + /// Returns whether the view contains data or not. bool has_data() const { return this->get_count() > 0; } + /// Returns whether the view contains mutable data or not. bool has_mutable_data() const { return this->has_data() && this->data_is_mutable_; } + /// Returns a reference to the element of 1d immutable view at specified location. + /// + /// @note This method does not perform boundary checks in release build. + /// In debug build, the method asserts that the index is out of the bounds. + /// + /// @note Should be used carefully in performance-critical parts of the code + /// due to the absence of inlining. + /// + /// @param id The index of the element to be returned. template > const T& at(std::int64_t id) const { ONEDAL_ASSERT(has_data()); @@ -247,6 +321,16 @@ class ndview : public ndarray_base { return *(get_data() + id); } + /// Returns a reference to the element of 2d immutable view at specified location. + /// + /// @note This method does not perform boundary checks in release build. + /// In debug build, the method asserts that the index is out of the bounds. + /// + /// @note Should be used carefully in performance-critical parts of the code + /// due to the absence of inlining. + /// + /// @param id0 The index of the element along the ``0``-th axis. + /// @param id1 The index of the element along the ``1``-st axis. template > const T& at(std::int64_t id0, std::int64_t id1) const { ONEDAL_ASSERT(has_data()); @@ -262,6 +346,9 @@ class ndview : public ndarray_base { } } + /// Returns a reference to the element of 1d mutable view at specified location. + /// + /// @param id The index of the element to be returned. template > T& at(std::int64_t id) { ONEDAL_ASSERT(has_mutable_data()); @@ -269,6 +356,10 @@ class ndview : public ndarray_base { return *(get_mutable_data() + id); } + /// Returns a reference to the element of 2d mutable view at specified location. + /// + /// @param id0 The index of the element along the ``0``-th axis. + /// @param id1 The index of the element along the ``1``-st axis. template > T& at(std::int64_t id0, std::int64_t id1) { ONEDAL_ASSERT(has_mutable_data()); @@ -285,11 +376,22 @@ class ndview : public ndarray_base { } #ifdef ONEDAL_DATA_PARALLEL + /// Returns a copy of the element of 1d immutable view located in USM at specified location. + /// + /// @param queue The SYCL* queue object. + /// @param id The index of the element to be returned. + /// @param deps The vector of events that the operation depends on. template > T at_device(sycl::queue& queue, std::int64_t id, const event_vector& deps = {}) const { return this->get_slice(id, id + 1).to_host(queue, deps).at(0); } + /// Returns a copy of the element of 2d immutable view located in USM at specified location. + /// + /// @param queue The SYCL* queue object. + /// @param id0 The index of the element along the ``0``-th axis. + /// @param id1 The index of the element along the ``1``-st axis. + /// @param deps The vector of events that the operation depends on. template > T at_device(sycl::queue& queue, std::int64_t id0, @@ -302,6 +404,13 @@ class ndview : public ndarray_base { } #endif // ONEDAL_DATA_PARALLEL + /// Get transposed multidimensional view. + /// The shape and strides of the transposed multidimensional view are swapped. + /// + /// The data is not modified or copied: The transposed ndview points to the same memory block + /// as the original ndview. + /// + /// @return The transposed multidimensional view. auto t() const { using tranposed_ndview_t = ndview>; const auto& shape = this->get_shape(); @@ -309,6 +418,16 @@ class ndview : public ndarray_base { return tranposed_ndview_t{ data_, shape.t(), strides.t(), data_is_mutable_ }; } + /// Get the multidimensional view of the data reshaped to the requested shape. + /// The total number of elements in the reshaped view must remain the same. + /// The data is not copied: the reshaped ndview points to the same memory block + /// as the original ndview. + /// + /// @tparam new_axis_count The number of dimensions in the reshaped multidimensional view. + /// + /// @param new_shape The shape of the reshaped multidimensional view. + /// + /// @return The reshaped multidimensional view. template auto reshape(const ndshape& new_shape) const { check_reshape_conditions(new_shape); @@ -316,6 +435,15 @@ class ndview : public ndarray_base { return reshaped_ndview_t{ data_, new_shape, data_is_mutable_ }; } + /// Get 1-dimensional slice of 1-dimensional view. + /// The slice is a view into the original memory block. + /// The data is not copied: The sliced view points to the data within the same memory block + /// as the original ndview. + /// + /// @param from The starting index of the data slice within the input view. + /// @param to The ending index of the data slice within the input view. + /// + /// @return The 1-dimensional view with a data slice. template > ndview get_slice(std::int64_t from, std::int64_t to) const { ONEDAL_ASSERT((this->get_dimension(0) >= from) && (from >= 0)); @@ -326,6 +454,16 @@ class ndview : public ndarray_base { return ndview(new_start_point, new_shape, this->get_strides(), this->data_is_mutable_); } + /// Get 2-dimensional row slice of 2-dimensional view. + /// The slice is a view into the original memory block. + /// The data is not copied: The sliced view points to the data within the same memory block + /// as the original ndview. + /// + /// @param from_row The starting row index of the data slice within the input view. + /// @param to_row The ending row index of the data slice within the input view. + /// + /// @return The 2-dimensional view with a data slice containing data rows [from_row, ..., to_row) + /// from the original view. template > ndview get_row_slice(std::int64_t from_row, std::int64_t to_row) const { ONEDAL_ASSERT((this->get_dimension(0) >= from_row) && (from_row >= 0)); @@ -340,39 +478,74 @@ class ndview : public ndarray_base { return ndview(new_start_point, new_shape, this->get_strides(), this->data_is_mutable_); } + /// Get 2-dimensional column slice of 2-dimensional view. + /// The slice is a view into the original memory block. + /// The data is not copied: The sliced view points to the data within the same memory block + /// as the original ndview. + /// + /// @param from_col The starting column index of the data slice within the input view. + /// @param to_col The ending column index of the data slice within the input view. + /// + /// @return The 2-dimensional view with a data slice containing data columns [from_col, ..., to_col) + /// from the original view. template > ndview get_col_slice(std::int64_t from_col, std::int64_t to_col) const { return this->t().get_row_slice(from_col, to_col).t(); } #ifdef ONEDAL_DATA_PARALLEL + /// Creates a multidimensional array with the same shape as the view, + /// but having the data allocated on host. The data from the view is copied to the array on host. + /// + /// @param q The SYCL* queue object. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The new multidimensional array instance. ndarray to_host(sycl::queue& q, const event_vector& deps = {}) const; + + /// Creates a multidimensional array with the same shape as the view, + /// but having the data allocated in USM on device. + /// The data from the view is copied to the array on device. + /// + /// @param q The SYCL* queue object. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The new multidimensional array instance. ndarray to_device(sycl::queue& q, const event_vector& deps = {}) const; -#endif -#ifdef ONEDAL_DATA_PARALLEL + /// Prefetches the data from high bandwidth memory to local cache. + /// Should be submitted ahead the expected computations to have enough time for data transfer. + /// + /// @param queue The SYCL* queue object. + /// + /// @return The SYCL* event object indicating the availability of the data in the view for reading + /// and writing. sycl::event prefetch(sycl::queue& queue) const { return queue.prefetch(data_, this->get_count()); } #endif + /// Returns the iterator to the first element of the 1-dimensional view. template > T* begin() { ONEDAL_ASSERT(data_is_mutable_); return get_mutable_data(); } + /// Returns the iterator to the past-the-last element of the 1-dimensional view. template > T* end() { ONEDAL_ASSERT(data_is_mutable_); return get_mutable_data() + this->get_count(); } + /// Returns the constant iterator to the first element of the 1-dimensional view. template > const T* cbegin() const { return get_data(); } + /// Returns the constant iterator to the past-the-last element of the 1-dimensional view. template > const T* cend() const { return get_data() + this->get_count(); @@ -584,6 +757,8 @@ class ndarray : public ndview { /// @param shape The shape of the created multidimensional array. /// @param deleter The deleter that is called on the ``data`` when the last ndarray that refers it /// is out of the scope. + /// + /// @return The new multidimensional array instance. template > static ndarray wrap(T* data, const shape_t& shape, Deleter&& deleter = Deleter{}) { auto shared = shared_t{ data, std::forward(deleter) }; @@ -600,6 +775,8 @@ class ndarray : public ndview { /// @param shape The shape of the created multidimensional array. /// @param deleter The deleter that is called on the ``data`` when the last ndarray that refers it /// is out of the scope. + /// + /// @return The new multidimensional array instance. template > static ndarray wrap(const T* data, const shape_t& shape, Deleter&& deleter = Deleter{}) { auto shared = shared_t{ const_cast(data), std::forward(deleter) }; @@ -611,6 +788,8 @@ class ndarray : public ndview { /// /// @param data The shared pointer to a homogeneous data block. /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray wrap(const shared_t& data, const shape_t& shape) { return ndarray{ data, shape }; } @@ -620,6 +799,8 @@ class ndarray : public ndview { /// /// @param data R-value reference to the shared pointer to a homogeneous data block. /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray wrap(shared_t&& data, const shape_t& shape) { return ndarray{ std::move(data), shape }; } @@ -629,6 +810,8 @@ class ndarray : public ndview { /// /// @param ary The array that stores a homogeneous data block. /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray wrap(const array_t& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); return wrap(ary.get_data(), shape, array_deleter{ ary }); @@ -638,6 +821,8 @@ class ndarray : public ndview { /// /// @param ary The r-value reference to array that stores a homogeneous data block. /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray wrap(array_t&& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); const T* data_ptr = ary.get_data(); @@ -648,6 +833,8 @@ class ndarray : public ndview { /// The created ndarray shares data ownership with the given array. /// /// @param ary The array that stores a homogeneous data block. + /// + /// @return The new 1d ndarray instance. static ndarray wrap(const array_t& ary) { static_assert(axis_count == 1); return wrap(ary, shape_t{ ary.get_count() }); @@ -657,6 +844,8 @@ class ndarray : public ndview { /// The created ndarray shares data ownership with the given array. /// /// @param ary The r-value reference to array that stores a homogeneous data block. + /// + /// @return The new 1d ndarray instance. static ndarray wrap(array_t&& ary) { static_assert(axis_count == 1); std::int64_t ary_count = ary.get_count(); @@ -668,6 +857,8 @@ class ndarray : public ndview { /// /// @param ary The array that stores a homogeneous data block. /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray wrap_mutable(const array_t& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); auto shared = shared_t{ ary.get_mutable_data(), array_deleter{ ary } }; @@ -678,6 +869,8 @@ class ndarray : public ndview { /// /// @param ary The r-value reference to array that stores a homogeneous data block. /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray wrap_mutable(array_t&& ary, const shape_t& shape) { ONEDAL_ASSERT(ary.get_count() == shape.get_count()); T* data_ptr = ary.get_mutable_data(); @@ -689,6 +882,8 @@ class ndarray : public ndview { /// The created ndarray shares data ownership with the given array. /// /// @param ary The array that stores a homogeneous data block. + /// + /// @return The new 1d ndarray instance. static ndarray wrap_mutable(const array_t& ary) { static_assert(axis_count == 1); return wrap_mutable(ary, shape_t{ ary.get_count() }); @@ -697,7 +892,9 @@ class ndarray : public ndview { /// Creates a 1d ndarray instance by moving a mutable input array. /// The created ndarray shares data ownership with the given array. /// - /// @param shape The shape of the created multidimensional array. + /// @param ary The array that stores a homogeneous data block. + /// + /// @return The new 1d ndarray instance. static ndarray wrap_mutable(array_t&& ary) { static_assert(axis_count == 1); std::int64_t ary_count = ary.get_count(); @@ -707,6 +904,8 @@ class ndarray : public ndview { /// Creates an uninitialized multidimensional array of a requested shape. /// /// @param ary The r-value reference to array that stores a homogeneous data block. + /// + /// @return The new multidimensional array instance. static ndarray empty(const shape_t& shape) { T* ptr = dal::detail::malloc(dal::detail::default_host_policy{}, shape.get_count()); return wrap(ptr, @@ -719,6 +918,8 @@ class ndarray : public ndview { /// /// @param data The pointer to a homogeneous data block. /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray copy(const T* data, const shape_t& shape) { auto ary = empty(shape); ary.assign(data, shape.get_count()); @@ -728,6 +929,8 @@ class ndarray : public ndview { /// Creates a multidimensional array of the requested shape and fills it with zeros. /// /// @param shape The shape of the created multidimensional array. + /// + /// @return The new multidimensional array instance. static ndarray zeros(const shape_t& shape) { auto ary = empty(shape); ary.fill(T(0)); @@ -741,6 +944,8 @@ class ndarray : public ndview { /// @param q The SYCL* queue object. /// @param shape The shape of the created multidimensional array. /// @param alloc_kind The kind of USM to be allocated. + /// + /// @return The new multidimensional array instance. static ndarray empty(const sycl::queue& q, const shape_t& shape, const sycl::usm::alloc& alloc_kind = sycl::usm::alloc::shared) { @@ -756,6 +961,9 @@ class ndarray : public ndview { /// @param data The pointer to a homogeneous data block. /// @param shape The shape of the created multidimensional array. /// @param alloc_kind The kind of USM to be allocated. + /// + /// @return A tuple with the created multidimensional array and the SYCL* event object + /// indicating the availability of the resulting array for reading and writing. static std::tuple copy( sycl::queue& q, const T* data, @@ -766,6 +974,17 @@ class ndarray : public ndview { return { ary, event }; } + /// Creates a multidimensional array of the requested shape with the elements + /// stored in SYCL* USM and fills it with a scalar value provided. + /// + /// @param q The SYCL* queue object. + /// @param shape The shape of the created multidimensional array. + /// @param value The scalar value to fill the array with. + /// @param alloc_kind The kind of USM to be allocated. + /// @param deps The vector of events that the operation depends on. + /// + /// @return A tuple with the created multidimensional array and the SYCL* event object + /// indicating the availability of the resulting array for reading and writing. static std::tuple full( sycl::queue& q, const shape_t& shape, @@ -777,6 +996,15 @@ class ndarray : public ndview { return { ary, event }; } + /// Creates a multidimensional array of the requested shape with the elements + /// stored in SYCL* USM and fills it with zeros. + /// + /// @param q The SYCL* queue object. + /// @param shape The shape of the created multidimensional array. + /// @param alloc_kind The kind of USM to be allocated. + /// + /// @return A tuple with the created multidimensional array and the SYCL* event object + /// indicating the availability of the resulting array for reading and writing. static std::tuple zeros( sycl::queue& q, const shape_t& shape, @@ -784,6 +1012,15 @@ class ndarray : public ndview { return full(q, shape, T(0), alloc_kind); } + /// Creates a multidimensional array of the requested shape with the elements + /// stored in SYCL* USM and fills it with ones. + /// + /// @param q The SYCL* queue object. + /// @param shape The shape of the created multidimensional array. + /// @param alloc_kind The kind of USM to be allocated. + /// + /// @return A tuple with the created multidimensional array and the SYCL* event object + /// indicating the availability of the resulting array for reading and writing. static std::tuple ones( sycl::queue& q, const shape_t& shape, @@ -792,21 +1029,40 @@ class ndarray : public ndview { } #endif + /// Get ndview sub-object of the ndarray. + /// + /// @return The ndview sub-object. const base& get_view() const { return *this; } + /// Get 1d dal::array that shares the ownership on the data block of this ndarray. + /// + /// @return The 1d dal::array that contains all the data from this multidimentional array. array_t flatten() const { return array_t{ data_, this->get_count() }; } #ifdef ONEDAL_DATA_PARALLEL + /// Get 1d dal::array that shares the ownership on the SYCL* USM data block of this ndarray. + /// + /// @param q The SYCL* queue object. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The 1d dal::array that contains all the USM data from this multidimentional array. array_t flatten(sycl::queue& q, const event_vector& deps = {}) const { ONEDAL_ASSERT(is_known_usm(q, data_.get())); return array_t{ q, data_, this->get_count(), deps }; } #endif + /// Get transposed multidimensional array. + /// The shape and strides of the transposed multidimensional array are swapped. + /// + /// The data is not copied: The transposed ndarray shares the ownership on the data block + /// with the original ndarray. + /// + /// @return The transposed multidimensional array. auto t() const { using tranposed_ndarray_t = ndarray>; const auto& shape = this->get_shape(); @@ -815,6 +1071,16 @@ class ndarray : public ndview { this->has_mutable_data()); } + /// Get the multidimensional array reshaped to the requested shape. + /// The total number of elements in the reshaped array must remain the same. + /// The data is not copied: the reshaped ndarray shares the ownership on the data block + /// with the original ndarray. + /// + /// @tparam new_axis_count The number of dimensions in the reshaped multidimensional array. + /// + /// @param new_shape The shape of the reshaped multidimensional array. + /// + /// @return The reshaped multidimensional array. template auto reshape(const ndshape& new_shape) const { using reshaped_ndarray_t = ndarray; @@ -822,6 +1088,9 @@ class ndarray : public ndview { return reshaped_ndarray_t{ data_, new_shape }.set_mutability(this->has_mutable_data()); } + /// Fill multidimensional array with a scalar value. + /// + /// @param value The scalar value to fill the array with. void fill(T value) { T* data_ptr = this->get_mutable_data(); for (std::int64_t i = 0; i < this->get_count(); i++) { @@ -830,6 +1099,14 @@ class ndarray : public ndview { } #ifdef ONEDAL_DATA_PARALLEL + /// Fill multidimensional array with a scalar value. + /// + /// @param q The SYCL* queue object. + /// @param value The scalar value to fill the array with. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The SYCL* event object indicating the availability of the array + /// for reading and writing. sycl::event fill(sycl::queue& q, T value, const event_vector& deps = {}) { auto data_ptr = this->get_mutable_data(); ONEDAL_ASSERT(is_known_usm(q, data_ptr)); @@ -840,6 +1117,8 @@ class ndarray : public ndview { } #endif + /// Fill multidimensional array with the values from a sequence 0, 1, 2, ..., N-1, + /// where N is the total number of elements in the array. void arange() { T* data_ptr = this->get_mutable_data(); for (std::int64_t i = 0; i < this->get_count(); i++) { @@ -848,6 +1127,14 @@ class ndarray : public ndview { } #ifdef ONEDAL_DATA_PARALLEL + /// Fill multidimensional array with the values from a sequence 0, 1, 2, ..., N-1, + /// where N is the total number of elements in the array. + /// + /// @param q The SYCL* queue object. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The SYCL* event object indicating the availability of the array + /// for reading and writing. sycl::event arange(sycl::queue& q, const event_vector& deps = {}) { auto data_ptr = this->get_mutable_data(); ONEDAL_ASSERT(is_known_usm(q, data_ptr)); @@ -861,6 +1148,10 @@ class ndarray : public ndview { } #endif + /// Copy the values from the input pointer to a memory block into multidimensional array. + /// + /// @param source_ptr The pointer to a homogeneous data block. + /// @param source_count The number of elements in the input memory block. void assign(const T* source_ptr, std::int64_t source_count) { ONEDAL_ASSERT(source_ptr != nullptr); ONEDAL_ASSERT(source_count > 0); @@ -869,6 +1160,15 @@ class ndarray : public ndview { } #ifdef ONEDAL_DATA_PARALLEL + /// Copy the values from the input pointer to SYCL* USM memory block into multidimensional array. + /// + /// @param q The SYCL* queue object. + /// @param source_ptr The pointer to a homogeneous data block. + /// @param source_count The number of elements in the input memory block. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The SYCL* event object indicating the availability of the array + /// for reading and writing. sycl::event assign(sycl::queue& q, const T* source_ptr, std::int64_t source_count, @@ -879,6 +1179,16 @@ class ndarray : public ndview { return dal::backend::copy(q, this->get_mutable_data(), source_ptr, source_count, deps); } + /// Copy the values from the input pointer to a memory block allocated on host + /// into multidimensional array. + /// + /// @param q The SYCL* queue object. + /// @param source_ptr The pointer to a homogeneous data block allocated in host memory. + /// @param source_count The number of elements in the input memory block. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The SYCL* event object indicating the availability of the array + /// for reading and writing. sycl::event assign_from_host(sycl::queue& q, const T* source_ptr, std::int64_t source_count, @@ -893,12 +1203,30 @@ class ndarray : public ndview { deps); } + /// Copy the values from the input multidimensional array + /// into this multidimensional array. + /// + /// @param q The SYCL* queue object. + /// @param src The multidimensional array to copy data from. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The SYCL* event object indicating the availability of the array + /// for reading and writing. sycl::event assign(sycl::queue& q, const ndarray& src, const event_vector& deps = {}) { ONEDAL_ASSERT(src.get_count() > 0); ONEDAL_ASSERT(src.get_count() <= this->get_count()); return this->assign(q, src.get_data(), src.get_count(), deps); } + /// Copy the values from the input multidimensional array containing data allocated on host + /// into this multidimensional array. + /// + /// @param q The SYCL* queue object. + /// @param src The multidimensional array to copy data from. + /// @param deps The vector of events that the operation depends on. + /// + /// @return The SYCL* event object indicating the availability of the array + /// for reading and writing. sycl::event assign_from_host(sycl::queue& q, const ndarray& src, const event_vector& deps = {}) { @@ -908,6 +1236,15 @@ class ndarray : public ndview { } #endif + /// Get a slice of the multidimensional array along the specified axis. + /// The slice is a view into the original multidimensional array. + /// The data is not copied: The sliced ndarray shares the ownership on the data block. + /// + /// @param offset The offset along the specified axis. + /// @param count The number of elements along the specified axis. + /// @param axis The axis to slice along. Only axis ``0`` is supported. + /// + /// @return The multidimensional array with a data slice. ndarray slice(std::int64_t offset, std::int64_t count, std::int64_t axis = 0) const { ONEDAL_ASSERT(order == ndorder::c, "Only C-order is supported"); ONEDAL_ASSERT(axis == 0, "Non-zero axis is not supported"); @@ -929,6 +1266,15 @@ class ndarray : public ndview { } #ifdef ONEDAL_DATA_PARALLEL + + /// Split a multidimensional array into multiple slices along the specified axis. + /// The slices are views into the original multidimensional array. + /// The data is not copied: The sliced ndarrays share the ownership on the data block. + /// + /// @param fold_count The number of slices to split the multidimensional array into. + /// @param axis The axis to split along. Only axis ``0`` is supported. + /// + /// @return A vector of multidimensional arrays with data slices. std::vector split(std::int64_t fold_count, std::int64_t axis = 0) const { ONEDAL_ASSERT(order == ndorder::c, "Only C-order is supported"); ONEDAL_ASSERT(axis == 0, "Non-zero axis is not supported"); @@ -984,6 +1330,8 @@ class ndarray : public ndview { }; #ifdef ONEDAL_DATA_PARALLEL + + template ndarray ndview::to_host( sycl::queue& q, @@ -996,9 +1344,7 @@ ndarray ndview::to_host( this->get_shape(), dal::detail::make_default_delete(dal::detail::default_host_policy{})); } -#endif -#ifdef ONEDAL_DATA_PARALLEL template ndarray ndview::to_device( sycl::queue& q, @@ -1012,9 +1358,6 @@ ndarray ndview::to_device( .wait_and_throw(); return dev; } -#endif - -#ifdef ONEDAL_DATA_PARALLEL template Date: Wed, 18 Dec 2024 03:31:01 -0800 Subject: [PATCH 4/5] Improve descriptions of backend primitives classes --- cpp/oneapi/dal/backend/primitives/ndarray.hpp | 6 +- .../data-management/backend-primitives.rst | 69 ++++++++++++++++++- .../api/data-management/backend/ndarray.rst | 4 +- .../api/data-management/backend/ndview.rst | 34 +++++++++ docs/source/conf.py | 11 +++ .../data-management/backend-primitives.rst | 33 ++++++++- 6 files changed, 152 insertions(+), 5 deletions(-) create mode 100644 docs/source/api/data-management/backend/ndview.rst diff --git a/cpp/oneapi/dal/backend/primitives/ndarray.hpp b/cpp/oneapi/dal/backend/primitives/ndarray.hpp index 6681b23d2fd..37ff272c5dd 100644 --- a/cpp/oneapi/dal/backend/primitives/ndarray.hpp +++ b/cpp/oneapi/dal/backend/primitives/ndarray.hpp @@ -23,8 +23,10 @@ namespace oneapi::dal::backend::primitives { enum class ndorder { - c, /* C-style ordering, row-major in 2D case */ - f /* Fortran-style ordering, column-major in 2D case */ + /// C-style ordering, row-major in 2D case + c, + /// Fortran-style ordering, column-major in 2D case + f }; template diff --git a/docs/source/api/data-management/backend-primitives.rst b/docs/source/api/data-management/backend-primitives.rst index fccc2cddee5..b95c3011ed2 100644 --- a/docs/source/api/data-management/backend-primitives.rst +++ b/docs/source/api/data-management/backend-primitives.rst @@ -16,7 +16,7 @@ .. highlight:: cpp - .. _api_dm_backend_primitives: +.. _api_dm_backend_primitives: ================== Backend Primitives @@ -34,6 +34,73 @@ All types and functions in this section are declared in the ``oneapi::dal::backend::primitives`` namespace and be available via inclusion of the ``oneapi/dal/backend/primitives/ndarray.hpp`` header file. +.. _api_dm_ndorder: + +Multidimensional array order +---------------------------- + +Refers to data indexing order, or how a linear sequence is translated into a multi-dimensional array. + +.. onedal_enumclass:: oneapi::dal::backend::primitives::ndorder + +.. _api_dm_ndshape: + +Multidimensional array shape +---------------------------- + +.. onedal_class:: oneapi::dal::backend::primitives::ndshape + +Multidimensional data view (ndview) +----------------------------------- + +An implementation of a multidimensional data container that provides a view of the homogeneous +data stored in an externally-managed memory block. + +All the ``ndview`` class methods can be divided into several groups: + +#. The group of ``wrap()`` methods that are used to create an ``ndview`` object from external, + mutable or immutable memory. + +#. The group of ``wrap_mutable()`` methods that are used to create a mutable ``ndview`` object from + ``dal::array`` object. + +#. The methods that are used to access the data. + +#. The methods like ``t()`` and ``reshape()`` that are used to change the shape and layout of the data view. + +#. The group of data slicing methods that are used to create a new ``ndview`` object that is a + view of the original data slice along some dimension. + +#. The group of data transfering methods that are used to produce a new ``ndview`` object that + contains the data copied from the original one, but at the different memory location. + +Multidimensional array (ndarray) +-------------------------------- + +An implementation of multidimensional data array that provides a way to store and manipulate +homogeneous data in a multidimensional structure. + +All the ``ndarray`` class methods can be divided into several groups: + +#. The group of ``wrap()`` and ``wrap_mutable()`` methods that are used to create an ``ndarray`` + object from external, mutable or immutable memory. + +#. The group of ``wrap()`` and ``wrap_mutable()`` methods that are used to create an ``ndarray`` + that shares its data with another data object. + +#. The group of methods like ``zeros()``, ``full()``, ``arange()``, etc. that are used to create an ``ndarray`` + object with the specified shape and values. + +#. The methods like ``t()`` and ``reshape()`` that are used to change the shape and layout + of the multidimensional array. + +#. The group of data slicing methods that are used to create a new ``ndarray`` object that is a view + of the original data slice along some dimension. + +#. The group of methods like ``fill()``, ``assign()``, ``assign_from_host()``, etc. that are used to + fill the array with the specified values. + .. toctree:: + backend/ndview.rst backend/ndarray.rst diff --git a/docs/source/api/data-management/backend/ndarray.rst b/docs/source/api/data-management/backend/ndarray.rst index 3fc1c794fcb..637ea37d66f 100644 --- a/docs/source/api/data-management/backend/ndarray.rst +++ b/docs/source/api/data-management/backend/ndarray.rst @@ -20,7 +20,9 @@ Multidimensional array ====================== -The ``ndarray`` class provides ... +The ``ndarray`` class provides a way to store and manipulate homogeneous data +in a multidimensional structure. +The pointer to the data within the ``ndarray`` object is :term:`reference-counted `:. --------------------- Programming interface diff --git a/docs/source/api/data-management/backend/ndview.rst b/docs/source/api/data-management/backend/ndview.rst new file mode 100644 index 00000000000..29f6552c12a --- /dev/null +++ b/docs/source/api/data-management/backend/ndview.rst @@ -0,0 +1,34 @@ +.. ****************************************************************************** +.. * Copyright contributors to the oneDAL project +.. * +.. * Licensed under the Apache License, Version 2.0 (the "License"); +.. * you may not use this file except in compliance with the License. +.. * You may obtain a copy of the License at +.. * +.. * http://www.apache.org/licenses/LICENSE-2.0 +.. * +.. * Unless required by applicable law or agreed to in writing, software +.. * distributed under the License is distributed on an "AS IS" BASIS, +.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. * See the License for the specific language governing permissions and +.. * limitations under the License. +.. *******************************************************************************/ + +.. _api_ndview: + +===================== +Multidimensional view +===================== + +The ``ndview`` class provides a view of the homogeneous data as a multidimensional structure +stored in an externally-managed memory block. + +--------------------- +Programming interface +--------------------- + +All types and functions in this section are declared in the +``oneapi::dal::backend::primitives`` namespace and be available via inclusion of the +``oneapi/dal/table/ndarray.hpp`` header file. + +.. onedal_class:: oneapi::dal::backend::primitives::ndview diff --git a/docs/source/conf.py b/docs/source/conf.py index 38841def0b1..863053d3270 100644 --- a/docs/source/conf.py +++ b/docs/source/conf.py @@ -131,6 +131,7 @@ nitpick_ignore = [ # top level namespace ('cpp:identifier', 'dal'), + ('cpp:identifier', 'base'), # method ('cpp:identifier', 'method'), ('cpp:identifier', 'Method'), @@ -140,6 +141,7 @@ ('cpp:identifier', 'Task'), # detail ('cpp:identifier', 'dal::detail'), + ('cpp:identifier', 'dal::detail::empty_delete'), ('cpp:identifier', 'detail'), ('cpp:identifier', 'detail::descriptor_base<>'), ('cpp:identifier', 'detail::descriptor_base<>::float_t'), @@ -400,13 +402,22 @@ ('cpp:identifier', 'sycl'), ('cpp:identifier', 'sycl::event'), ('cpp:identifier', 'sycl::queue'), + ('cpp:identifier', 'sycl::range'), ('cpp:identifier', 'sycl::usm'), + ('cpp:identifier', 'sycl::usm::alloc'), + ('cpp:identifier', 'sycl::usm::alloc::shared'), # backend primitives - data management ('cpp:identifier', 'array_t'), + ('cpp:identifier', 'axis_count'), ('cpp:identifier', 'ndarray'), + ('cpp:identifier', 'ndindex'), ('cpp:identifier', 'ndorder'), + ('cpp:identifier', 'ndorder::c'), ('cpp:identifier', 'ndshape'), + ('cpp:identifier', 'ndshape'), + ('cpp:identifier', 'ndview'), + ('cpp:identifier', 'order'), ('cpp:identifier', 'shape_t'), ('cpp:identifier', 'shared_t') ] diff --git a/docs/source/onedal/data-management/backend-primitives.rst b/docs/source/onedal/data-management/backend-primitives.rst index ab563bbc280..0d282a8adf9 100644 --- a/docs/source/onedal/data-management/backend-primitives.rst +++ b/docs/source/onedal/data-management/backend-primitives.rst @@ -22,4 +22,35 @@ Backend Primitives ================== -This section describes the types related to internal backend data management primitives. \ No newline at end of file +This section describes the types related to data management backend primitives. + +.. tabularcolumns:: |\Y{0.2}|\Y{0.8}| + +.. list-table:: Data Management Backend Primitives Types + :header-rows: 1 + :widths: 10 70 + :class: longtable + + * - Type + - Description + + * - :ref:`api_ndorder` + - An enumeration of multidimensional data orders used to store + contiguous data blocks inside the table. + + * - :ref:`api_ndshape` + - A class that represents the shape of a multidimensional array. + + * - :ref:`api_ndview` + - An implementation of a multidimensional data container that provides a view of the homogeneous + data stored in an externally-managed memory block. + + * - :ref:`api_ndarray` + - A class that provides a way to store and manipulate homogeneous data + in a multidimensional structure. + +--------------------- +Programming interface +--------------------- + +Refer to :ref:`API: Data Management Backend Primitives `. From cbca09632b012c6da969e56ef907afcb52e50720 Mon Sep 17 00:00:00 2001 From: Victoriya Fedotova Date: Wed, 18 Dec 2024 04:39:15 -0800 Subject: [PATCH 5/5] Correct license --- .../data-management/backend-primitives.rst | 34 +++++++++---------- .../api/data-management/backend/ndarray.rst | 28 +++++++-------- .../api/data-management/backend/ndview.rst | 28 +++++++-------- .../data-management/backend-primitives.rst | 30 ++++++++-------- 4 files changed, 56 insertions(+), 64 deletions(-) diff --git a/docs/source/api/data-management/backend-primitives.rst b/docs/source/api/data-management/backend-primitives.rst index b95c3011ed2..4cfb8262a82 100644 --- a/docs/source/api/data-management/backend-primitives.rst +++ b/docs/source/api/data-management/backend-primitives.rst @@ -1,22 +1,20 @@ -.. ****************************************************************************** -.. * Copyright contributors to the oneDAL project -.. * -.. * Licensed under the Apache License, Version 2.0 (the "License"); -.. * you may not use this file except in compliance with the License. -.. * You may obtain a copy of the License at -.. * -.. * http://www.apache.org/licenses/LICENSE-2.0 -.. * -.. * Unless required by applicable law or agreed to in writing, software -.. * distributed under the License is distributed on an "AS IS" BASIS, -.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -.. * See the License for the specific language governing permissions and -.. * limitations under the License. -.. *******************************************************************************/ +.. Copyright contributors to the oneDAL project +.. +.. Licensed under the Apache License, Version 2.0 (the "License"); +.. you may not use this file except in compliance with the License. +.. You may obtain a copy of the License at +.. +.. http://www.apache.org/licenses/LICENSE-2.0 +.. +.. Unless required by applicable law or agreed to in writing, software +.. distributed under the License is distributed on an "AS IS" BASIS, +.. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. See the License for the specific language governing permissions and +.. limitations under the License. .. highlight:: cpp -.. _api_dm_backend_primitives: +.. _api_backend_primitives: ================== Backend Primitives @@ -34,7 +32,7 @@ All types and functions in this section are declared in the ``oneapi::dal::backend::primitives`` namespace and be available via inclusion of the ``oneapi/dal/backend/primitives/ndarray.hpp`` header file. -.. _api_dm_ndorder: +.. _api_ndorder: Multidimensional array order ---------------------------- @@ -43,7 +41,7 @@ Refers to data indexing order, or how a linear sequence is translated into a mul .. onedal_enumclass:: oneapi::dal::backend::primitives::ndorder -.. _api_dm_ndshape: +.. _api_ndshape: Multidimensional array shape ---------------------------- diff --git a/docs/source/api/data-management/backend/ndarray.rst b/docs/source/api/data-management/backend/ndarray.rst index 637ea37d66f..81dd2d8281f 100644 --- a/docs/source/api/data-management/backend/ndarray.rst +++ b/docs/source/api/data-management/backend/ndarray.rst @@ -1,18 +1,16 @@ -.. ****************************************************************************** -.. * Copyright contributors to the oneDAL project -.. * -.. * Licensed under the Apache License, Version 2.0 (the "License"); -.. * you may not use this file except in compliance with the License. -.. * You may obtain a copy of the License at -.. * -.. * http://www.apache.org/licenses/LICENSE-2.0 -.. * -.. * Unless required by applicable law or agreed to in writing, software -.. * distributed under the License is distributed on an "AS IS" BASIS, -.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -.. * See the License for the specific language governing permissions and -.. * limitations under the License. -.. *******************************************************************************/ +.. Copyright contributors to the oneDAL project +.. +.. Licensed under the Apache License, Version 2.0 (the "License"); +.. you may not use this file except in compliance with the License. +.. You may obtain a copy of the License at +.. +.. http://www.apache.org/licenses/LICENSE-2.0 +.. +.. Unless required by applicable law or agreed to in writing, software +.. distributed under the License is distributed on an "AS IS" BASIS, +.. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. See the License for the specific language governing permissions and +.. limitations under the License. .. _api_ndarray: diff --git a/docs/source/api/data-management/backend/ndview.rst b/docs/source/api/data-management/backend/ndview.rst index 29f6552c12a..f5909c57df1 100644 --- a/docs/source/api/data-management/backend/ndview.rst +++ b/docs/source/api/data-management/backend/ndview.rst @@ -1,18 +1,16 @@ -.. ****************************************************************************** -.. * Copyright contributors to the oneDAL project -.. * -.. * Licensed under the Apache License, Version 2.0 (the "License"); -.. * you may not use this file except in compliance with the License. -.. * You may obtain a copy of the License at -.. * -.. * http://www.apache.org/licenses/LICENSE-2.0 -.. * -.. * Unless required by applicable law or agreed to in writing, software -.. * distributed under the License is distributed on an "AS IS" BASIS, -.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -.. * See the License for the specific language governing permissions and -.. * limitations under the License. -.. *******************************************************************************/ +.. Copyright contributors to the oneDAL project +.. +.. Licensed under the Apache License, Version 2.0 (the "License"); +.. you may not use this file except in compliance with the License. +.. You may obtain a copy of the License at +.. +.. http://www.apache.org/licenses/LICENSE-2.0 +.. +.. Unless required by applicable law or agreed to in writing, software +.. distributed under the License is distributed on an "AS IS" BASIS, +.. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. See the License for the specific language governing permissions and +.. limitations under the License. .. _api_ndview: diff --git a/docs/source/onedal/data-management/backend-primitives.rst b/docs/source/onedal/data-management/backend-primitives.rst index 0d282a8adf9..5826c5d00a3 100644 --- a/docs/source/onedal/data-management/backend-primitives.rst +++ b/docs/source/onedal/data-management/backend-primitives.rst @@ -1,18 +1,16 @@ -.. ****************************************************************************** -.. * Copyright contributors to the oneDAL project -.. * -.. * Licensed under the Apache License, Version 2.0 (the "License"); -.. * you may not use this file except in compliance with the License. -.. * You may obtain a copy of the License at -.. * -.. * http://www.apache.org/licenses/LICENSE-2.0 -.. * -.. * Unless required by applicable law or agreed to in writing, software -.. * distributed under the License is distributed on an "AS IS" BASIS, -.. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -.. * See the License for the specific language governing permissions and -.. * limitations under the License. -.. *******************************************************************************/ +.. Copyright contributors to the oneDAL project +.. +.. Licensed under the Apache License, Version 2.0 (the "License"); +.. you may not use this file except in compliance with the License. +.. You may obtain a copy of the License at +.. +.. http://www.apache.org/licenses/LICENSE-2.0 +.. +.. Unless required by applicable law or agreed to in writing, software +.. distributed under the License is distributed on an "AS IS" BASIS, +.. WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +.. See the License for the specific language governing permissions and +.. limitations under the License. .. highlight:: cpp @@ -53,4 +51,4 @@ This section describes the types related to data management backend primitives. Programming interface --------------------- -Refer to :ref:`API: Data Management Backend Primitives `. +Refer to :ref:`API: Data Management Backend Primitives `.