diff --git a/include/aidge/data/Interpolation.hpp b/include/aidge/data/Interpolation.hpp index 69a827f474b8110accfb247003014740855b1426..897bffe08b4e00000fb9f1888f93090a936cb86d 100644 --- a/include/aidge/data/Interpolation.hpp +++ b/include/aidge/data/Interpolation.hpp @@ -12,7 +12,8 @@ #ifndef AIDGE_CORE_UTILS_INTERPOLATION_H_ #define AIDGE_CORE_UTILS_INTERPOLATION_H_ -#include <cstdint> +#include <cstdint> // std::int64_t +#include <utility> // std::pair #include <vector> #include "aidge/operator/Pad.hpp" @@ -28,7 +29,7 @@ class Interpolation { * points retrieved by interpolation are out of bound, hence their coords * can be < 0 */ - using Coords = std::vector<int64_t>; + using Coords = std::vector<std::int64_t>; /** * @brief type alias to designate a point of any type : hence coordinates & * associated value diff --git a/include/aidge/operator/Pad.hpp b/include/aidge/operator/Pad.hpp index f2da306bba6ad3d7e0f78b3c3caaf96b61b42fe7..181a4e88a0fe30e2a86c44adda2195d7e6f5293d 100644 --- a/include/aidge/operator/Pad.hpp +++ b/include/aidge/operator/Pad.hpp @@ -26,16 +26,12 @@ namespace Aidge { enum class PadAttr { BeginEndBorders, BorderType, BorderValue }; -enum class PadBorderType { +enum class PadBorderType { /** @brief all out of bound values will be set to a given value.*/ Constant, - Edge, - Reflect, - Wrap, - /** @brief all out of bound values will take the value - *of their nearest neighbour - */ - Nearest, + Edge, + Reflect, + Wrap, /** @brief all out of bound values will be set to 0.*/ Zero, }; diff --git a/include/aidge/operator/Resize.hpp b/include/aidge/operator/Resize.hpp index ee6009dae8d9e042b60a1a42c0eeccd1f9b676aa..20a27073c4cad68186d1629df9f6b7ddbbaa217e 100644 --- a/include/aidge/operator/Resize.hpp +++ b/include/aidge/operator/Resize.hpp @@ -37,7 +37,7 @@ enum class ResizeAttr { // extrapolation_value, // keep_aspect_ratio_policy, InterpolationMode, - PaddingMode, + PaddingMode }; /** @@ -219,7 +219,7 @@ class Resize_Op * used if interpolation_mode = Interpolation::Mode::Cubic * @warning Scales & ROI input cannot be set simultaneously. If bot are set, * forward will fail. - * @warning Padding mode will tell how values out of bound are treated. + * @warning Padding mode will tell how values out of bound are treated. * @return NodePtr */ std::shared_ptr<Node> @@ -238,6 +238,7 @@ const char *const EnumStrings<Aidge::ResizeAttr>::data[] = { "coordinateTransformationMode", "cubicCoeffA", "InterpolationMode", + "PaddingMode" }; } #endif /* AIDGE_CORE_OPERATOR_RESIZE_H_ */ diff --git a/src/data/Tensor.cpp b/src/data/Tensor.cpp index c43ca3fbe211ef3ebcb9e335c8373237cd21239f..6cb113a3c6d06076006b9755b96185044cd8aafa 100644 --- a/src/data/Tensor.cpp +++ b/src/data/Tensor.cpp @@ -720,9 +720,8 @@ bool Tensor::isInBounds(const std::vector<DimSize_t>& tensorDims, const std::vec "the same number of dimension as tensor dimensions({}), aborting.", coords, tensorDims); - T i; bool isInBound {true}; - for(i = 0 ; i < static_cast<T>(coords.size()) && isInBound; ++i ){ + for(std::size_t i = 0 ; i < coords.size() && isInBound; ++i ){ isInBound = coords[i] >= 0 && coords[i] < static_cast<T>(tensorDims[i]) ; } return isInBound; diff --git a/src/data/interpolation.cpp b/src/data/interpolation.cpp index 64eb63e701724e82638813bbee9eac89f4b52070..59d40cbb8b8194c277417ca715a427a752cbc5cb 100644 --- a/src/data/interpolation.cpp +++ b/src/data/interpolation.cpp @@ -11,13 +11,13 @@ #include "aidge/data/Interpolation.hpp" -#include <algorithm> +#include <algorithm> // std::clamp #include <bitset> -#include <cmath> -#include <cstddef> -#include <cstdint> -#include <stdexcept> -#include <utility> +#include <cmath> // std::ceil, std::floor +#include <cstddef> // std::size_t +#include <cstdint> // std::int64_t +#include <stdexcept> // std::runtime_error +#include <utility> // std::make_pair, std::set #include <vector> #include "aidge/data/Tensor.hpp" @@ -61,8 +61,7 @@ std::vector<float> Interpolation::untransformCoordinates( "Got coords to transform ({}) and outputDims ({})", transformedCoords, outputDims); - std::vector<float> originalCoords; - originalCoords.resize(transformedCoords.size()); + std::vector<float> originalCoords(transformedCoords.size()); for (DimIdx_t i = 0; i < transformedCoords.size(); ++i) { float scale = static_cast<float>(outputDims[i]) / @@ -129,42 +128,37 @@ Interpolation::retrieveNeighbours(const T *tensorValues, Log::debug("retrieveNeighbours: coords to interpolate : {}", coords); // Will retrieve out of bound values depending on given padding mode. - auto retrieveOutOfBoundValue = - [&tensorValues, &tensorDims, &paddingMode](Coords coord) -> T { - std::vector<DimSize_t> rectifiedCoord; - rectifiedCoord.reserve(coord.size()); - switch (paddingMode) { - case Aidge::PadBorderType::Nearest: { - for (DimSize_t i = 0; i < coord.size(); ++i) { - rectifiedCoord[i] = - std::clamp<int64_t>(coord[i], - 0, - static_cast<int64_t>(tensorDims[i])); - } - return tensorValues[Tensor::getIdx(tensorDims, rectifiedCoord)]; - } - case Aidge::PadBorderType::Zero: { - return static_cast<T>(0); - } - default: { - AIDGE_THROW_OR_ABORT( - std::runtime_error, - "Unsupported padding mode as of now for interpolation."); - } - } - }; + // auto retrieveOutOfBoundValue = + // [&tensorValues, &tensorDims, &paddingMode](Coords coord) -> T { + // std::vector<DimSize_t> rectifiedCoord; + // rectifiedCoord.reserve(coord.size()); + // switch (paddingMode) { + // case Aidge::PadBorderType::Edge: { + // for (DimSize_t i = 0; i < coord.size(); ++i) { + // rectifiedCoord[i] = coord[i] < 0 ? 0 : tensorDims[i] - 1; + // } + // return tensorValues[Tensor::getIdx(tensorDims, rectifiedCoord)]; + // } + // case Aidge::PadBorderType::Zero: { + // return static_cast<T>(0); + // } + // default: { + // AIDGE_THROW_OR_ABORT( + // std::runtime_error, + // "Unsupported padding mode as of now for interpolation."); + // } + // } + // }; std::set<Point<T>> neighbours; - std::bitset<MaxDim> bits; - DimSize_t nbNeighbours = pow(2, tensorDims.size()); - Coords neighbourCoords; - neighbourCoords.resize(tensorDims.size()); + const std::size_t nbNeighbours = std::size_t(1) << tensorDims.size(); + Coords neighbourCoords(tensorDims.size()); - for (DimSize_t i = 0; i < nbNeighbours; ++i) { - bits = std::bitset<MaxDim>{i}; + for (std::size_t i = 0; i < nbNeighbours; ++i) { + const std::bitset<MaxDim> bits = std::bitset<MaxDim>{i}; for (size_t j = 0; j < tensorDims.size(); ++j) { neighbourCoords[j] = - bits[j] == 0 ? ceil(coords[j]) : std::floor(coords[j]); + bits[j] == 0 ? std::ceil(coords[j]) : std::floor(coords[j]); } T value; @@ -176,7 +170,26 @@ Interpolation::retrieveNeighbours(const T *tensorValues, std::vector<DimSize_t>(neighbourCoords.begin(), neighbourCoords.end()))]; } else { - value = retrieveOutOfBoundValue(neighbourCoords); + switch (paddingMode) { + case PadBorderType::Edge: + for (DimSize_t j = 0; j < tensorDims.size(); ++j) { + neighbourCoords[j] = (neighbourCoords[j] < 0) ? 0 : + ((neighbourCoords[j] >= static_cast<std::int64_t>(tensorDims[j])) ? (tensorDims[j] - 1) : + neighbourCoords[j]); + } + value = tensorValues[Tensor::getIdx( + tensorDims, + std::vector<DimSize_t>(neighbourCoords.begin(), + neighbourCoords.end()))]; + break; + case PadBorderType::Zero: + value = static_cast<T>(0); + break; + default: + AIDGE_THROW_OR_ABORT( + std::runtime_error, + "Unsupported padding mode as of now for interpolation."); + } } neighbours.insert(std::make_pair(neighbourCoords, value)); }