Review ReorgYolo class for shape inference aspects (#18633)
* Add static shape adapter - Adapters holds CPU dimension which can be reference to it or vector - Add ov::optional for holding optional result from shape inference - Add new `infer` function in `IStaticShapeInfer` * Temporary support of StaticShape * Minor corrections in ShapeInferenceTA * Migrate shape_infer to new interface version * Replace StaticShape by adapter implementation * Replace IShapeInferCommon by IStaticShapeInfer * Correct code formatting * Fix build issues * NodeValidationFailure::create for StaticShapeRef * Review ReorgYolo op for shape inference - Check partial shape and label propagation - Check shape_infer implementation - Update tests for static and dynamic shapes * Change dim::is_valid to dim::is_empty
This commit is contained in:
1 parent
e2c3d0fe73
commit
5a4cf4c8b6
8 files changed
+238
-118
No files matched your search
@@ -35,9 +35,8 @@ public:
|
||||
Strides get_strides() const {
|
||||
return m_strides;
|
||||
}
|
||||
void set_strides(Strides strides) {
|
||||
m_strides = std::move(strides);
|
||||
}
|
||||
|
||||
void set_strides(const size_t stride);
|
||||
|
||||
private:
|
||||
Strides m_strides;
|
||||
|
||||
@@ -216,6 +216,36 @@ auto floor_div(const TDim& dim, const typename TDim::value_type divisor) -> TDim
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Check if dimension is empty.
|
||||
*
|
||||
* For static dimension the empty dimension is equal to zero dimension.
|
||||
*
|
||||
* @tparam TDim Dimension type.
|
||||
* @param d Dimension for check.
|
||||
* @return true if dimension is empty otherwise false.
|
||||
*/
|
||||
template <class TDim,
|
||||
typename std::enable_if<!std::is_same<Dimension, typename std::decay<TDim>::type>::value>::type* = nullptr>
|
||||
bool is_empty(TDim&& d) {
|
||||
return d == typename std::decay<TDim>::type{};
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Check if dimension is empty.
|
||||
*
|
||||
* For iv::Dimension the empty means that has no dimension at all.
|
||||
*
|
||||
* @tparam TDim Dimension type.
|
||||
* @param d Dimension for check.
|
||||
* @return true if dimension is empty otherwise false.
|
||||
*/
|
||||
template <class TDim,
|
||||
typename std::enable_if<std::is_same<Dimension, typename std::decay<TDim>::type>::value>::type* = nullptr>
|
||||
bool is_empty(TDim&& d) {
|
||||
return d.get_interval().empty();
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Check if dimension is evenly divisible.
|
||||
*
|
||||
@@ -226,12 +256,7 @@ auto floor_div(const TDim& dim, const typename TDim::value_type divisor) -> TDim
|
||||
*/
|
||||
template <class TDim>
|
||||
bool is_divisible(const TDim& quotient, const typename TDim::value_type dividend) {
|
||||
return quotient / dividend != TDim{};
|
||||
}
|
||||
|
||||
template <>
|
||||
inline bool is_divisible<Dimension>(const Dimension& quotient, const typename Dimension::value_type dividend) {
|
||||
return !(quotient / dividend).get_interval().empty();
|
||||
return !is_empty(quotient / dividend);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -258,7 +283,6 @@ void scale(TDim& d, float scale) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace dim
|
||||
} // namespace util
|
||||
} // namespace ov
|
||||
@@ -4,55 +4,50 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <openvino/core/validation_util.hpp>
|
||||
#include <openvino/op/reorg_yolo.hpp>
|
||||
|
||||
#include "compare.hpp"
|
||||
#include "dimension_util.hpp"
|
||||
#include "openvino/op/reorg_yolo.hpp"
|
||||
#include "utils.hpp"
|
||||
|
||||
namespace ov {
|
||||
namespace op {
|
||||
namespace v0 {
|
||||
|
||||
template <class T, class TRShape = result_shape_t<T>>
|
||||
std::vector<TRShape> shape_infer(const ReorgYolo* op, const std::vector<T>& input_shapes) {
|
||||
NODE_VALIDATION_CHECK(op, (input_shapes.size() == 1));
|
||||
NODE_VALIDATION_CHECK(op, input_shapes.size() == 1);
|
||||
using namespace ov::util;
|
||||
|
||||
const auto& input_shape = input_shapes[0];
|
||||
const auto& input_rank = input_shape.rank();
|
||||
const auto stride = op->get_strides().front();
|
||||
|
||||
auto output_shapes = std::vector<TRShape>(1);
|
||||
auto& output_shape = output_shapes[0];
|
||||
const auto& strides = op->get_strides();
|
||||
|
||||
if (input_shape.rank().is_static()) {
|
||||
NODE_VALIDATION_CHECK(op, input_shape.size() == 4, "[N, C, H, W] input shape is required.");
|
||||
NODE_SHAPE_INFER_CHECK(op, input_shapes, input_shape.size() == 4, "[N, C, H, W] input shape is required.");
|
||||
|
||||
NODE_VALIDATION_CHECK(op,
|
||||
input_shape[2].is_dynamic() || (input_shape[2].get_length() % strides[0]) == 0,
|
||||
"For [N, C, H, W] input shape, H should be divisible by stride.");
|
||||
const auto stride_sq = typename T::value_type(stride * stride);
|
||||
NODE_SHAPE_INFER_CHECK(
|
||||
op,
|
||||
input_shapes,
|
||||
input_shape[1].is_dynamic() || cmp::ge(input_shape[1].get_length(), stride_sq.get_length()),
|
||||
"For [N, C, H, W] input shape, C >= (stride*stride) is required.");
|
||||
|
||||
NODE_VALIDATION_CHECK(op,
|
||||
input_shape[3].is_dynamic() || (input_shape[3].get_length() % strides[0]) == 0,
|
||||
"For [N, C, H, W] input shape, W should be divisible by stride.");
|
||||
|
||||
NODE_VALIDATION_CHECK(op,
|
||||
input_shape[1].is_dynamic() ||
|
||||
static_cast<size_t>(input_shape[1].get_length()) >= (strides[0] * strides[0]),
|
||||
"For [N, C, H, W] input shape, C >= (stride*stride) is required.");
|
||||
|
||||
output_shape = TRShape({input_shape[0], input_shape[1]});
|
||||
|
||||
for (size_t i = 2; i < input_shape.size(); i++) {
|
||||
if (input_shape[i].is_static())
|
||||
output_shape.push_back(input_shape[i].get_length() / strides[0]);
|
||||
else {
|
||||
const auto& interval = input_shape[i].get_interval();
|
||||
if (interval.has_upper_bound()) {
|
||||
output_shape.push_back(
|
||||
ov::Dimension(interval.get_min_val() / strides[0], interval.get_max_val() / strides[0]));
|
||||
} else {
|
||||
output_shape.push_back(ov::Dimension::dynamic());
|
||||
}
|
||||
}
|
||||
output_shape[1] *= strides[0];
|
||||
output_shape.reserve(input_shape.size());
|
||||
auto out_it = std::copy(input_shape.begin(), input_shape.begin() + 2, std::back_inserter(output_shape));
|
||||
for (size_t i = 2; i < input_shape.size(); ++i, ++out_it) {
|
||||
auto d = input_shape[i] / stride;
|
||||
NODE_SHAPE_INFER_CHECK(op,
|
||||
input_shapes,
|
||||
!dim::is_empty(d),
|
||||
"For [N, C, H, W] input shape, H and W should be divisible by stride.");
|
||||
out_it = std::move(d);
|
||||
}
|
||||
output_shape[1] *= stride_sq;
|
||||
} else {
|
||||
output_shape = ov::PartialShape::dynamic(input_shape.rank());
|
||||
output_shape = PartialShape::dynamic(input_rank);
|
||||
}
|
||||
return output_shapes;
|
||||
}
|
||||
|
||||
@@ -2,45 +2,48 @@
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#include "ngraph/op/reorg_yolo.hpp"
|
||||
#include "openvino/op/reorg_yolo.hpp"
|
||||
|
||||
#include "itt.hpp"
|
||||
#include "ngraph/runtime/reference/reorg_yolo.hpp"
|
||||
#include "reorg_yolo_shape_inference.hpp"
|
||||
|
||||
using namespace std;
|
||||
using namespace ngraph;
|
||||
|
||||
op::ReorgYolo::ReorgYolo(const Output<Node>& input, const Strides& strides) : Op({input}), m_strides(strides) {
|
||||
namespace ov {
|
||||
namespace op {
|
||||
namespace v0 {
|
||||
ReorgYolo::ReorgYolo(const Output<Node>& input, const Strides& strides) : Op({input}), m_strides(strides) {
|
||||
constructor_validate_and_infer_types();
|
||||
}
|
||||
|
||||
op::ReorgYolo::ReorgYolo(const Output<Node>& input, const size_t stride)
|
||||
: Op({input}),
|
||||
m_strides(std::vector<size_t>{stride, stride}) {
|
||||
ReorgYolo::ReorgYolo(const Output<Node>& input, const size_t stride) : Op({input}), m_strides(2, stride) {
|
||||
constructor_validate_and_infer_types();
|
||||
}
|
||||
|
||||
void op::ReorgYolo::validate_and_infer_types() {
|
||||
void ReorgYolo::validate_and_infer_types() {
|
||||
OV_OP_SCOPE(v0_ReorgYolo_validate_and_infer_types);
|
||||
NODE_VALIDATION_CHECK(this, !m_strides.empty(), "Stride attribute is required.");
|
||||
|
||||
auto input_et = get_input_element_type(0);
|
||||
|
||||
std::vector<ov::PartialShape> input_shapes = {get_input_partial_shape(0)};
|
||||
const auto input_shapes = std::vector<PartialShape>{get_input_partial_shape(0)};
|
||||
const auto output_shapes = shape_infer(this, input_shapes);
|
||||
|
||||
set_output_type(0, input_et, output_shapes[0]);
|
||||
set_output_type(0, get_input_element_type(0), output_shapes[0]);
|
||||
}
|
||||
|
||||
shared_ptr<Node> op::ReorgYolo::clone_with_new_inputs(const OutputVector& new_args) const {
|
||||
std::shared_ptr<Node> ReorgYolo::clone_with_new_inputs(const OutputVector& new_args) const {
|
||||
OV_OP_SCOPE(v0_ReorgYolo_clone_with_new_inputs);
|
||||
check_new_args_count(this, new_args);
|
||||
return make_shared<ReorgYolo>(new_args.at(0), m_strides);
|
||||
return std::make_shared<ReorgYolo>(new_args.at(0), m_strides);
|
||||
}
|
||||
|
||||
bool op::ReorgYolo::visit_attributes(AttributeVisitor& visitor) {
|
||||
bool ReorgYolo::visit_attributes(AttributeVisitor& visitor) {
|
||||
OV_OP_SCOPE(v0_ReorgYolo_visit_attributes);
|
||||
visitor.on_attribute("stride", m_strides);
|
||||
return true;
|
||||
}
|
||||
|
||||
void ReorgYolo::set_strides(const size_t stride) {
|
||||
m_strides.resize(2);
|
||||
std::fill_n(m_strides.begin(), 2, stride);
|
||||
}
|
||||
} // namespace v0
|
||||
} // namespace op
|
||||
} // namespace ov
|
||||
@@ -2,18 +2,38 @@
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#include <gmock/gmock.h>
|
||||
|
||||
#include "common_test_utils/test_assertions.hpp"
|
||||
#include "common_test_utils/type_prop.hpp"
|
||||
#include "gtest/gtest.h"
|
||||
#include "ngraph/ngraph.hpp"
|
||||
#include "openvino/opsets/opset12.hpp"
|
||||
|
||||
using namespace std;
|
||||
using namespace ngraph;
|
||||
using namespace ov;
|
||||
using namespace ov::opset12;
|
||||
using namespace testing;
|
||||
|
||||
TEST(type_prop, reorg_yolo_stride_2) {
|
||||
class TypePropReorgYoloTest : public TypePropOpTest<ov::op::v0::ReorgYolo> {};
|
||||
|
||||
TEST_F(TypePropReorgYoloTest, default_ctor) {
|
||||
const auto data = std::make_shared<Parameter>(element::f32, PartialShape{1, 4, {13, 16}, 4});
|
||||
|
||||
auto op = make_op();
|
||||
op->set_strides(2);
|
||||
op->set_arguments(OutputVector{data});
|
||||
op->validate_and_infer_types();
|
||||
|
||||
EXPECT_EQ(op->get_strides(), Strides({2, 2}));
|
||||
EXPECT_EQ(op->get_input_size(), 1);
|
||||
EXPECT_EQ(op->get_output_size(), 1);
|
||||
EXPECT_EQ(op->get_output_element_type(0), element::f32);
|
||||
EXPECT_EQ(op->get_output_partial_shape(0), PartialShape({1, 16, {7, 8}, 2}));
|
||||
}
|
||||
|
||||
TEST_F(TypePropReorgYoloTest, stride_2) {
|
||||
const auto in_shape = Shape{1, 64, 26, 26};
|
||||
size_t stride = 2;
|
||||
auto data_param = make_shared<op::Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
auto data_param = std::make_shared<Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_op(data_param, stride);
|
||||
|
||||
// in_shape [N,C,H,W] -> out_shape [N, C*stride*stride, H/stride, W/stride]
|
||||
Shape expected_shape = Shape{1, 256, 13, 13};
|
||||
@@ -21,34 +41,38 @@ TEST(type_prop, reorg_yolo_stride_2) {
|
||||
EXPECT_EQ(reorg_yolo->get_output_shape(0), expected_shape);
|
||||
}
|
||||
|
||||
TEST(type_prop, reorg_yolo_stride_2_dynamic_shape) {
|
||||
TEST_F(TypePropReorgYoloTest, stride_2_dynamic_shape) {
|
||||
const auto in_shape = PartialShape{-1, -1, -1, -1};
|
||||
size_t stride = 2;
|
||||
auto data_param = make_shared<op::Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
auto data_param = std::make_shared<Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_op(data_param, stride);
|
||||
|
||||
const auto expected_shape = PartialShape{-1, -1, -1, -1};
|
||||
|
||||
EXPECT_EQ(reorg_yolo->get_output_partial_shape(0), expected_shape);
|
||||
}
|
||||
|
||||
TEST(type_prop, reorg_yolo_stride_2_dynamic_shape_ranges) {
|
||||
const auto in_shape = PartialShape{{1, 4}, {3, 9}, {16, 32}, {16, 32}};
|
||||
TEST_F(TypePropReorgYoloTest, stride_2_interval_shape_with_labels) {
|
||||
auto in_shape = PartialShape{{1, 4}, {3, 9}, {16, 32}, {16, 32}};
|
||||
set_shape_labels(in_shape, 10);
|
||||
|
||||
size_t stride = 2;
|
||||
auto data_param = make_shared<op::Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
auto data_param = std::make_shared<Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_op(data_param, stride);
|
||||
|
||||
// in_shape [N,C,H,W] -> out_shape [N, C*stride*stride, H/stride, W/stride]
|
||||
const auto expected_shape = PartialShape{{1, 4}, {12, 36}, {8, 16}, {8, 16}};
|
||||
|
||||
EXPECT_EQ(reorg_yolo->get_output_partial_shape(0), expected_shape);
|
||||
EXPECT_THAT(get_shape_labels(reorg_yolo->get_output_partial_shape(0)),
|
||||
ElementsAre(10, no_label, no_label, no_label));
|
||||
}
|
||||
|
||||
TEST(type_prop, reorg_yolo_stride_2_batch_2) {
|
||||
TEST_F(TypePropReorgYoloTest, stride_2_batch_2) {
|
||||
const auto in_shape = Shape{2, 64, 26, 26};
|
||||
size_t stride = 2;
|
||||
auto data_param = make_shared<op::Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
auto data_param = std::make_shared<Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_op(data_param, stride);
|
||||
|
||||
// in_shape [N,C,H,W] -> out_shape [N, C*stride*stride, H/stride, W/stride]
|
||||
Shape expected_shape = Shape{2, 256, 13, 13};
|
||||
@@ -56,22 +80,22 @@ TEST(type_prop, reorg_yolo_stride_2_batch_2) {
|
||||
EXPECT_EQ(reorg_yolo->get_output_shape(0), expected_shape);
|
||||
}
|
||||
|
||||
TEST(type_prop, reorg_yolo_stride_2_smaller_H) {
|
||||
TEST_F(TypePropReorgYoloTest, stride_2_smaller_H) {
|
||||
const auto in_shape = Shape{1, 24, 34, 62};
|
||||
size_t stride = 2;
|
||||
auto data_param = make_shared<op::Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
auto data_param = std::make_shared<Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_op(data_param, stride);
|
||||
|
||||
// in_shape [N,C,H,W] -> out_shape [N, C*stride*stride, H/stride, W/stride]
|
||||
Shape expected_shape = Shape{1, 96, 17, 31};
|
||||
EXPECT_EQ(reorg_yolo->get_output_shape(0), expected_shape);
|
||||
}
|
||||
|
||||
TEST(type_prop, reorg_yolo_stride_3) {
|
||||
TEST_F(TypePropReorgYoloTest, stride_3) {
|
||||
const auto in_shape = Shape{1, 9, 3, 3};
|
||||
size_t stride = 3;
|
||||
auto data_param = make_shared<op::Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
auto data_param = std::make_shared<Parameter>(element::f32, in_shape);
|
||||
auto reorg_yolo = make_op(data_param, stride);
|
||||
|
||||
// in_shape [N,C,H,W] -> out_shape [N, C*stride*stride, H/stride, W/stride]
|
||||
Shape expected_shape =
|
||||
@@ -80,19 +104,48 @@ TEST(type_prop, reorg_yolo_stride_3) {
|
||||
EXPECT_EQ(reorg_yolo->get_output_shape(0), expected_shape);
|
||||
}
|
||||
|
||||
TEST(type_prop, reorg_yolo_catch_small_shape_stride) {
|
||||
TEST_F(TypePropReorgYoloTest, catch_small_shape_stride) {
|
||||
const auto in_shape = Shape{1, 1, 4, 4};
|
||||
size_t stride = 2;
|
||||
auto data_param = make_shared<op::Parameter>(element::f32, in_shape);
|
||||
try {
|
||||
// Throw error test: For [N, C, H, W] input shape, C >= (stride*stride) is required.
|
||||
auto reorg_yolo = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
auto data_param = std::make_shared<Parameter>(element::f32, in_shape);
|
||||
|
||||
// Should have thrown, so fail if it didn't
|
||||
FAIL() << "Incompatible stride was not detected.";
|
||||
} catch (const ngraph_error& error) {
|
||||
EXPECT_HAS_SUBSTRING(error.what(), std::string("stride"));
|
||||
} catch (...) {
|
||||
FAIL() << "Stride size check failed for unexpected reason.";
|
||||
}
|
||||
OV_EXPECT_THROW(std::ignore = make_op(data_param, stride), NodeValidationFailure, HasSubstr("stride"));
|
||||
}
|
||||
|
||||
TEST_F(TypePropReorgYoloTest, data_shape_not_compatible_rank_4) {
|
||||
const auto data_param = std::make_shared<Parameter>(element::f32, PartialShape{1, 1, {13, 14}, 4});
|
||||
|
||||
OV_EXPECT_THROW(std::ignore = make_op(std::make_shared<Parameter>(element::f32, PartialShape::dynamic(3)),
|
||||
static_cast<size_t>(2)),
|
||||
NodeValidationFailure,
|
||||
HasSubstr("[N, C, H, W] input shape is required"));
|
||||
|
||||
OV_EXPECT_THROW(std::ignore = make_op(std::make_shared<Parameter>(element::f32, PartialShape::dynamic(5)),
|
||||
static_cast<size_t>(2)),
|
||||
NodeValidationFailure,
|
||||
HasSubstr("[N, C, H, W] input shape is required"));
|
||||
}
|
||||
|
||||
TEST_F(TypePropReorgYoloTest, h_dim_not_div_by_stride) {
|
||||
const auto data_param = std::make_shared<Parameter>(element::f32, PartialShape{1, 9, 13, 3});
|
||||
|
||||
OV_EXPECT_THROW(std::ignore = make_op(data_param, static_cast<size_t>(3)),
|
||||
NodeValidationFailure,
|
||||
HasSubstr("H and W should be divisible by stride"));
|
||||
}
|
||||
|
||||
TEST_F(TypePropReorgYoloTest, w_dim_not_div_by_stride) {
|
||||
const auto data_param = std::make_shared<Parameter>(element::f32, Shape{1, 9, 6, 4});
|
||||
|
||||
OV_EXPECT_THROW(std::ignore = make_op(data_param, static_cast<size_t>(3)),
|
||||
NodeValidationFailure,
|
||||
HasSubstr("H and W should be divisible by stride"));
|
||||
}
|
||||
|
||||
TEST_F(TypePropReorgYoloTest, channels_lower_than_sq_stride) {
|
||||
const auto data_param = std::make_shared<Parameter>(element::f32, PartialShape{1, 8, 6, 6});
|
||||
|
||||
OV_EXPECT_THROW(std::ignore = make_op(data_param, static_cast<size_t>(3)),
|
||||
NodeValidationFailure,
|
||||
HasSubstr(" C >= (stride*stride) is required."));
|
||||
}
|
||||
+67
@@ -0,0 +1,67 @@
|
||||
|
||||
// Copyright (C) 2018-2023 Intel Corporation
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include "common_test_utils/test_assertions.hpp"
|
||||
#include "reorg_yolo_shape_inference.hpp"
|
||||
#include "utils.hpp"
|
||||
|
||||
using namespace ov;
|
||||
using namespace ov::intel_cpu;
|
||||
using namespace testing;
|
||||
|
||||
class StaticShapeReorgYoloTest : public OpStaticShapeInferenceTest<op::v0::ReorgYolo> {};
|
||||
|
||||
TEST_F(StaticShapeReorgYoloTest, default_ctor_no_args) {
|
||||
op = make_op();
|
||||
op->set_strides(3);
|
||||
|
||||
input_shapes = ShapeVector{{2, 9, 12, 6}};
|
||||
shape_inference(op.get(), input_shapes, output_shapes);
|
||||
|
||||
EXPECT_EQ(output_shapes.size(), 1);
|
||||
EXPECT_EQ(output_shapes.front(), StaticShape({2, 81, 4, 2}));
|
||||
}
|
||||
|
||||
TEST_F(StaticShapeReorgYoloTest, data_input_is_dynamic_rank) {
|
||||
const auto data = std::make_shared<op::v0::Parameter>(element::f32, ov::PartialShape::dynamic());
|
||||
op = make_op(data, 2);
|
||||
|
||||
input_shapes = ShapeVector{{2, 12, 12, 24}};
|
||||
shape_inference(op.get(), input_shapes, output_shapes);
|
||||
|
||||
EXPECT_EQ(output_shapes.size(), 1);
|
||||
EXPECT_EQ(output_shapes.front(), StaticShape({2, 48, 6, 12}));
|
||||
}
|
||||
|
||||
TEST_F(StaticShapeReorgYoloTest, data_input_is_static_rank) {
|
||||
const auto data = std::make_shared<op::v0::Parameter>(element::f32, ov::PartialShape::dynamic(4));
|
||||
op = make_op(data, 2);
|
||||
|
||||
input_shapes = ShapeVector{{2, 20, 12, 24}};
|
||||
shape_inference(op.get(), input_shapes, output_shapes);
|
||||
|
||||
EXPECT_EQ(output_shapes.size(), 1);
|
||||
EXPECT_EQ(output_shapes.front(), StaticShape({2, 80, 6, 12}));
|
||||
}
|
||||
|
||||
TEST_F(StaticShapeReorgYoloTest, data_shape_not_compatible_rank_4) {
|
||||
const auto data = std::make_shared<op::v0::Parameter>(element::f32, PartialShape::dynamic());
|
||||
op = make_op(data, 2);
|
||||
|
||||
OV_EXPECT_THROW(shape_inference(op.get(), ShapeVector{{2, 20, 12, 24, 1}}, output_shapes),
|
||||
NodeValidationFailure,
|
||||
HasSubstr("[N, C, H, W] input shape is required"));
|
||||
}
|
||||
|
||||
TEST_F(StaticShapeReorgYoloTest, h_dim_not_div_by_stride) {
|
||||
const auto data = std::make_shared<op::v0::Parameter>(element::f32, PartialShape::dynamic());
|
||||
op = make_op(data, 2);
|
||||
|
||||
OV_EXPECT_THROW(shape_inference(op.get(), ShapeVector{{2, 20, 11, 24}}, output_shapes),
|
||||
NodeValidationFailure,
|
||||
HasSubstr("H and W should be divisible by stride"));
|
||||
}
|
||||
@@ -1,20 +0,0 @@
|
||||
|
||||
// Copyright (C) 2018-2023 Intel Corporation
|
||||
// SPDX-License-Identifier: Apache-2.0
|
||||
//
|
||||
|
||||
#include <reorg_yolo_shape_inference.hpp>
|
||||
|
||||
#include "utils.hpp"
|
||||
|
||||
using namespace ov;
|
||||
using namespace ov::intel_cpu;
|
||||
using namespace std;
|
||||
|
||||
TEST(StaticShapeInferenceTest, ReorgYoloV0) {
|
||||
size_t stride = 2;
|
||||
auto data_param = make_shared<op::v0::Parameter>(element::f32, ov::PartialShape{-1, -1, -1, -1});
|
||||
auto op = make_shared<op::v0::ReorgYolo>(data_param, stride);
|
||||
|
||||
check_static_shape(op.get(), {StaticShape{1, 64, 26, 26}}, {StaticShape{1, 256, 13, 13}});
|
||||
}
|
||||
@@ -37,8 +37,7 @@ std::vector<layout> reorg_yolo_inst::calc_output_layouts(reorg_yolo_node const&
|
||||
auto output_format = input_layout.format;
|
||||
|
||||
ov::op::v0::ReorgYolo op;
|
||||
std::vector<size_t> strides { static_cast<size_t>(desc->stride) };
|
||||
op.set_strides(strides);
|
||||
op.set_strides(static_cast<size_t>(desc->stride));
|
||||
|
||||
std::vector<ShapeType> input_shapes = {
|
||||
input_layout.get<ShapeType>()
|
||||
|
||||
Reference in new issue
Block a user