Remove obsoleted v0::Broadcast and BroadcastLike operators (#2779)
[platform/upstream/dldt.git] / ngraph / test / eval.cpp
1 //*****************************************************************************
2 // Copyright 2017-2020 Intel Corporation
3 //
4 // Licensed under the Apache License, Version 2.0 (the "License");
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 //     http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //*****************************************************************************
16
17 #include <cmath>
18 #include <cstddef>
19 #include <string>
20 #include <vector>
21
22 #include "gmock/gmock.h"
23 #include "gtest/gtest.h"
24
25 #include "ngraph/node.hpp"
26 #include "ngraph/node_output.hpp"
27 #include "ngraph/op/abs.hpp"
28 #include "ngraph/op/acos.hpp"
29 #include "ngraph/op/add.hpp"
30 #include "ngraph/op/asin.hpp"
31 #include "ngraph/op/atan.hpp"
32 #include "ngraph/op/broadcast.hpp"
33 #include "ngraph/op/ceiling.hpp"
34 #include "ngraph/op/concat.hpp"
35 #include "ngraph/op/constant.hpp"
36 #include "ngraph/op/convert.hpp"
37 #include "ngraph/op/cos.hpp"
38 #include "ngraph/op/cosh.hpp"
39 #include "ngraph/op/erf.hpp"
40 #include "ngraph/op/exp.hpp"
41 #include "ngraph/op/floor.hpp"
42 #include "ngraph/op/gather.hpp"
43 #include "ngraph/op/log.hpp"
44 #include "ngraph/op/max_pool.hpp"
45 #include "ngraph/op/min.hpp"
46 #include "ngraph/op/minimum.hpp"
47 #include "ngraph/op/negative.hpp"
48 #include "ngraph/op/non_zero.hpp"
49 #include "ngraph/op/not.hpp"
50 #include "ngraph/op/parameter.hpp"
51 #include "ngraph/op/range.hpp"
52 #include "ngraph/op/reduce_logical_and.hpp"
53 #include "ngraph/op/relu.hpp"
54 #include "ngraph/op/reshape.hpp"
55 #include "ngraph/op/round.hpp"
56 #include "ngraph/op/scatter_elements_update.hpp"
57 #include "ngraph/op/scatter_update.hpp"
58 #include "ngraph/op/shape_of.hpp"
59 #include "ngraph/op/sigmoid.hpp"
60 #include "ngraph/op/sign.hpp"
61 #include "ngraph/op/sin.hpp"
62 #include "ngraph/op/sinh.hpp"
63 #include "ngraph/op/sqrt.hpp"
64 #include "ngraph/op/squeeze.hpp"
65 #include "ngraph/op/stop_gradient.hpp"
66 #include "ngraph/op/tan.hpp"
67 #include "ngraph/op/tanh.hpp"
68 #include "ngraph/op/topk.hpp"
69 #include "ngraph/op/transpose.hpp"
70 #include "ngraph/op/unsqueeze.hpp"
71 #include "ngraph/runtime/host_tensor.hpp"
72 #include "ngraph/validation_util.hpp"
73 #include "util/all_close_f.hpp"
74 #include "util/ndarray.hpp"
75 #include "util/test_tools.hpp"
76 #include "util/type_prop.hpp"
77
78 NGRAPH_SUPPRESS_DEPRECATED_START
79
80 using namespace std;
81 using namespace ngraph;
82
83 #define ASSERT_FLOAT_VECTORS_EQ(expected, result)                                                  \
84     ASSERT_EQ(expected.size(), result.size()) << "Array sizes differ.";                            \
85     for (size_t i = 0; i < expected.size(); ++i)                                                   \
86     {                                                                                              \
87         ASSERT_FLOAT_EQ(expected[i], result[i]) << "at index: " << i;                              \
88     }
89
90 TEST(eval, bad_get_data_ptr)
91 {
92     HostTensor c(element::f32, Shape{});
93     *c.get_data_ptr<float>() = 1.0;
94     EXPECT_EQ(*c.get_data_ptr<element::Type_t::f32>(), 1.0);
95     try
96     {
97         c.get_data_ptr<element::Type_t::f64>();
98         FAIL() << "Bad type not detected.";
99     }
100     catch (const CheckFailure& error)
101     {
102         EXPECT_HAS_SUBSTRING(error.what(), std::string("get_data_ptr"));
103     }
104     try
105     {
106         c.get_data_ptr<element::Type_t::i32>();
107         FAIL() << "Bad type not detected.";
108     }
109     catch (const CheckFailure& error)
110     {
111         EXPECT_HAS_SUBSTRING(error.what(), std::string("get_data_ptr"));
112     }
113 }
114
115 TEST(eval, max_eval_parameter)
116 {
117     auto p = make_shared<op::Parameter>(element::i64, Shape{});
118
119     auto result = maximum_value(p);
120     EXPECT_FALSE(result.first);
121     EXPECT_EQ(result.second, numeric_limits<uint64_t>::max());
122 }
123
124 TEST(eval, max_eval_constant)
125 {
126     auto c = op::Constant::create<int64_t>(element::i64, Shape{}, {27});
127     auto result = maximum_value(c);
128     ASSERT_TRUE(result.first);
129     EXPECT_EQ(result.second, 27);
130 }
131
132 TEST(eval, max_eval_minimum_constant)
133 {
134     auto c = op::Constant::create<int64_t>(element::i64, Shape{}, {27});
135     auto p = make_shared<op::Parameter>(element::i64, Shape{});
136     auto m = make_shared<op::Minimum>(c, p);
137     auto result = maximum_value(m);
138     ASSERT_TRUE(result.first);
139     EXPECT_EQ(result.second, 27);
140 }
141
142 TEST(eval, max_eval_reduce_min)
143 {
144     auto concat = make_shared<op::v0::Convert>(
145         make_shared<op::v0::Concat>(
146             OutputVector{make_shared<op::v0::Parameter>(element::i64, Shape{4}),
147                          make_shared<op::v0::Constant>(element::i64, Shape{4}, 37)},
148             0),
149         element::i32);
150     auto reduce = make_shared<op::v0::Convert>(
151         make_shared<op::v1::ReduceMin>(concat,
152                                        make_shared<op::v0::Constant>(element::i32, Shape{1}, 0)),
153         element::i64);
154     auto squeezes = make_shared<op::v0::Squeeze>(
155         make_shared<op::v0::Unsqueeze>(reduce,
156                                        make_shared<op::v0::Constant>(element::i32, Shape{1}, 0)),
157         make_shared<op::v0::Constant>(element::i64, Shape{1}, 0));
158     EXPECT_EQ(maximum_value(squeezes).second, 37);
159 }
160
161 TEST(eval, evaluate_shape_of)
162 {
163     auto p = make_shared<op::Parameter>(element::f32, PartialShape{-1, -1});
164     auto so = make_shared<op::v0::ShapeOf>(p);
165     auto fun = make_shared<Function>(OutputVector{so}, ParameterVector{p});
166     auto result = make_shared<HostTensor>();
167     ASSERT_TRUE(fun->evaluate({result},
168                               {make_host_tensor<element::Type_t::f32>(
169                                   Shape{2, 3}, {0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f})}));
170     EXPECT_EQ(result->get_element_type(), element::i64);
171     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2}));
172     auto result_shape = read_vector<int64_t>(result);
173     vector<int64_t> arg_shape{2, 3};
174     ASSERT_EQ(result_shape, arg_shape);
175 }
176
177 TEST(eval, evaluate_dynamic_range_sum)
178 {
179     auto p_start = make_shared<op::Parameter>(element::f32, PartialShape{});
180     auto p_stop = make_shared<op::Parameter>(element::f32, PartialShape{});
181     auto p_step = make_shared<op::Parameter>(element::f32, PartialShape{});
182     auto p1 = make_shared<op::Parameter>(element::f32, PartialShape{});
183     auto range = make_shared<op::v0::Range>(p_start, p_stop, p_step);
184     auto add = make_shared<op::v1::Add>(range, p1);
185     auto fun =
186         make_shared<Function>(OutputVector{add}, ParameterVector{p_start, p_stop, p_step, p1});
187     auto result_tensor = make_shared<HostTensor>();
188     ASSERT_TRUE(fun->evaluate({result_tensor},
189                               {make_host_tensor<element::Type_t::f32>({}, {1.0f}),
190                                make_host_tensor<element::Type_t::f32>({}, {10.0f}),
191                                make_host_tensor<element::Type_t::f32>({}, {3.0f}),
192                                make_host_tensor<element::Type_t::f32>({}, {7.0f})}));
193     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
194     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3}));
195     auto cval = read_vector<float>(result_tensor);
196     vector<float> seq{8.0f, 11.0f, 14.0f};
197     ASSERT_EQ(cval, seq);
198 }
199
200 #ifdef NGRAPH_INTERPRETER_ENABLE
201 TEST(eval, interpret_dynamic_range_sum)
202 {
203     auto p_start = make_shared<op::Parameter>(element::f32, PartialShape{});
204     auto p_stop = make_shared<op::Parameter>(element::f32, PartialShape{});
205     auto p_step = make_shared<op::Parameter>(element::f32, PartialShape{});
206     auto p1 = make_shared<op::Parameter>(element::f32, PartialShape{});
207     auto range = make_shared<op::v0::Range>(p_start, p_stop, p_step);
208     auto add = make_shared<op::v1::Add>(range, p1);
209     auto fun =
210         make_shared<Function>(OutputVector{add}, ParameterVector{p_start, p_stop, p_step, p1});
211     auto backend = runtime::Backend::create("INTERPRETER");
212     auto p_start_val = backend->create_tensor(element::f32, Shape{});
213     copy_data(p_start_val, vector<float>{1.0f});
214     auto p_stop_val = backend->create_tensor(element::f32, Shape{});
215     copy_data(p_stop_val, vector<float>{10.0f});
216     auto p_step_val = backend->create_tensor(element::f32, Shape{});
217     copy_data(p_step_val, vector<float>{3.0f});
218     auto p1_val = backend->create_tensor(element::f32, Shape{});
219     copy_data(p1_val, vector<float>{7.0f});
220     auto result = backend->create_tensor();
221     auto cfun = backend->compile(fun);
222     cfun->call({result}, {p_start_val, p_stop_val, p_step_val, p1_val});
223     EXPECT_EQ(result->get_element_type(), element::f32);
224     EXPECT_EQ(result->get_partial_shape(), (PartialShape{3}));
225     auto result_val = read_vector<float>(result);
226     vector<float> seq{8.0f, 11.0f, 14.0f};
227     ASSERT_EQ(result_val, seq);
228 }
229 #endif
230
231 TEST(eval, evaluate_broadcast_v3_bidirectional)
232 {
233     Shape shape_a{4, 1};
234     auto A = make_shared<op::Parameter>(element::f32, shape_a);
235     auto target_shape = op::Constant::create<int32_t>(element::i32, Shape{3}, {2, 1, 4});
236     auto bcast_v3 =
237         make_shared<op::v3::Broadcast>(A, target_shape, op::BroadcastType::BIDIRECTIONAL);
238     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A});
239
240     auto result = make_shared<HostTensor>();
241     ASSERT_TRUE(fun->evaluate(
242         {result}, {make_host_tensor<element::Type_t::f32>(Shape{4, 1}, {1.0f, 2.0f, 3.0f, 4.0f})}));
243     EXPECT_EQ(result->get_element_type(), element::f32);
244     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 4, 4}));
245     auto result_val = read_vector<float>(result);
246     vector<float> expec{1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4,
247                         1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4};
248     ASSERT_EQ(result_val, expec);
249 }
250
251 TEST(eval, evaluate_broadcast_v3_bidirectional_dyn)
252 {
253     Shape shape_a{4, 1};
254     auto A = make_shared<op::Parameter>(element::i32, shape_a);
255     auto target_shape = make_shared<op::Parameter>(element::i32, Shape{3});
256     auto bcast_v3 =
257         make_shared<op::v3::Broadcast>(A, target_shape, op::BroadcastType::BIDIRECTIONAL);
258     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A, target_shape});
259
260     auto result = make_shared<HostTensor>();
261     ASSERT_TRUE(fun->evaluate({result},
262                               {make_host_tensor<element::Type_t::i32>(Shape{4, 1}, {1, 2, 3, 4}),
263                                make_host_tensor<element::Type_t::i32>(Shape{3}, {2, 1, 4})}));
264     EXPECT_EQ(result->get_element_type(), element::i32);
265     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 4, 4}));
266     auto result_val = read_vector<int32_t>(result);
267     vector<int32_t> expec{1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4,
268                           1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4};
269     ASSERT_EQ(result_val, expec);
270 }
271
272 TEST(eval, evaluate_broadcast_v3_numpy)
273 {
274     Shape shape_a{3, 1};
275     auto A = make_shared<op::Parameter>(element::f32, shape_a);
276     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{3}, {2, 3, 6});
277     auto bcast_v3 = make_shared<op::v3::Broadcast>(A, target_shape);
278     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A});
279
280     auto result = make_shared<HostTensor>();
281     ASSERT_TRUE(fun->evaluate(
282         {result}, {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f})}));
283     EXPECT_EQ(result->get_element_type(), element::f32);
284     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
285     auto result_val = read_vector<float>(result);
286     vector<float> expec{
287         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
288         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
289     };
290     ASSERT_EQ(result_val, expec);
291 }
292
293 TEST(eval, evaluate_broadcast_v3_numpy_dyn)
294 {
295     Shape shape_a{3, 1};
296     auto A = make_shared<op::Parameter>(element::f32, shape_a);
297     auto target_shape = make_shared<op::Parameter>(element::i32, Shape{3});
298     auto bcast_v3 = make_shared<op::v3::Broadcast>(A, target_shape);
299     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A, target_shape});
300
301     auto result = make_shared<HostTensor>();
302     ASSERT_TRUE(
303         fun->evaluate({result},
304                       {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f}),
305                        make_host_tensor<element::Type_t::i32>(Shape{3}, {2, 3, 6})}));
306     EXPECT_EQ(result->get_element_type(), element::f32);
307     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
308     auto result_val = read_vector<float>(result);
309     vector<float> expec{
310         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
311         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
312     };
313     ASSERT_EQ(result_val, expec);
314 }
315
316 TEST(eval, evaluate_broadcast_v3_numpy_vs_bidi)
317 {
318     Shape in_shape{1, 4, 1};
319
320     auto A = make_shared<op::Parameter>(element::f32, in_shape);
321     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{3}, {1, 4, 4});
322     auto bcast_v3_num = make_shared<op::v3::Broadcast>(A, target_shape, op::BroadcastType::NUMPY);
323     auto fun_num = make_shared<Function>(OutputVector{bcast_v3_num}, ParameterVector{A});
324
325     auto result = make_shared<HostTensor>();
326     ASSERT_TRUE(fun_num->evaluate(
327         {result}, {make_host_tensor<element::Type_t::f32>(in_shape, {1.0f, 2.0f, 3.0f, 4.0f})}));
328     EXPECT_EQ(result->get_element_type(), element::f32);
329     EXPECT_EQ(result->get_partial_shape(), (PartialShape{1, 4, 4}));
330     auto result_val = read_vector<float>(result);
331     vector<float> expec{1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4};
332     ASSERT_EQ(expec, result_val);
333
334     auto target_shape2 = op::Constant::create<int64_t>(element::i64, Shape{2}, {1, 4});
335     auto bcast_v3 =
336         make_shared<op::v3::Broadcast>(A, target_shape2, op::BroadcastType::BIDIRECTIONAL);
337     auto fun_bidi = make_shared<Function>(OutputVector{bcast_v3_num}, ParameterVector{A});
338
339     auto result2 = make_shared<HostTensor>();
340     ASSERT_TRUE(fun_bidi->evaluate(
341         {result2}, {make_host_tensor<element::Type_t::f32>(in_shape, {1.0f, 2.0f, 3.0f, 4.0f})}));
342     EXPECT_EQ(result2->get_element_type(), element::f32);
343     EXPECT_EQ(result2->get_partial_shape(), (PartialShape{1, 4, 4}));
344     auto result_val2 = read_vector<float>(result2);
345     vector<float> expec2{1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4};
346     ASSERT_EQ(expec2, result_val2);
347 }
348
349 TEST(eval, evaluate_broadcast_v3_bidi_3d)
350 {
351     Shape in_shape{1, 4, 1};
352
353     auto A = make_shared<op::Parameter>(element::f32, in_shape);
354     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{3}, {1, 1, 3});
355     auto bcast_v3_num =
356         make_shared<op::v3::Broadcast>(A, target_shape, op::BroadcastType::BIDIRECTIONAL);
357     auto fun_num = make_shared<Function>(OutputVector{bcast_v3_num}, ParameterVector{A});
358
359     auto result = make_shared<HostTensor>();
360     ASSERT_TRUE(fun_num->evaluate(
361         {result}, {make_host_tensor<element::Type_t::f32>(in_shape, {1.0f, 2.0f, 3.0f, 4.0f})}));
362     EXPECT_EQ(result->get_element_type(), element::f32);
363     EXPECT_EQ(result->get_partial_shape(), (PartialShape{1, 4, 3}));
364     auto result_val = read_vector<float>(result);
365     vector<float> expec{1.0f, 1.0f, 1.0f, 2.0f, 2.0f, 2.0f, 3.0f, 3.0f, 3.0f, 4.0f, 4.0f, 4.0f};
366     ASSERT_EQ(expec, result_val);
367 }
368
369 TEST(eval, evaluate_broadcast_v3_bidi_4d)
370 {
371     Shape in_shape{4, 1, 1};
372     Shape expec_shape{1, 4, 2, 2};
373
374     auto A = make_shared<op::Parameter>(element::f32, in_shape);
375     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{4}, {1, 1, 2, 2});
376     auto bcast_v3 =
377         make_shared<op::v3::Broadcast>(A, target_shape, op::BroadcastType::BIDIRECTIONAL);
378     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A});
379
380     auto result = make_shared<HostTensor>();
381     ASSERT_TRUE(fun->evaluate(
382         {result}, {make_host_tensor<element::Type_t::f32>(in_shape, {1.0f, 2.0f, 3.0f, 4.0f})}));
383     EXPECT_EQ(result->get_element_type(), element::f32);
384     EXPECT_EQ(result->get_partial_shape(), (PartialShape{1, 4, 2, 2}));
385     auto result_val = read_vector<float>(result);
386     vector<float> expec{1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4};
387     ASSERT_EQ(result_val, expec);
388 }
389
390 TEST(eval, evaluate_broadcast_v3_pdpd)
391 {
392     Shape shape_a{3, 1};
393     auto A = make_shared<op::Parameter>(element::f32, shape_a);
394     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{3}, {2, 3, 6});
395     auto bcast_v3 = make_shared<op::v3::Broadcast>(
396         A, target_shape, op::BroadcastModeSpec(op::BroadcastType::PDPD, 1));
397     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A});
398
399     auto result = make_shared<HostTensor>();
400     ASSERT_TRUE(fun->evaluate(
401         {result}, {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f})}));
402     EXPECT_EQ(result->get_element_type(), element::f32);
403     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
404     auto result_val = read_vector<float>(result);
405     vector<float> expec{
406         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
407         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
408     };
409     ASSERT_EQ(result_val, expec);
410 }
411
412 TEST(eval, evaluate_broadcast_v3_pdpd_dyn)
413 {
414     Shape shape_a{3, 1};
415     auto A = make_shared<op::Parameter>(element::f32, shape_a);
416     auto target_shape = make_shared<op::Parameter>(element::i32, Shape{3});
417     auto bcast_v3 = make_shared<op::v3::Broadcast>(
418         A, target_shape, op::BroadcastModeSpec(op::BroadcastType::PDPD, 1));
419     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A, target_shape});
420
421     auto result = make_shared<HostTensor>();
422     ASSERT_TRUE(
423         fun->evaluate({result},
424                       {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f}),
425                        make_host_tensor<element::Type_t::i32>(Shape{3}, {2, 3, 6})}));
426     EXPECT_EQ(result->get_element_type(), element::f32);
427     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
428     auto result_val = read_vector<float>(result);
429     vector<float> expec{
430         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
431         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
432     };
433     ASSERT_EQ(result_val, expec);
434 }
435
436 TEST(eval, evaluate_broadcast_v1_numpy)
437 {
438     Shape shape_a{3, 1};
439     auto A = make_shared<op::Parameter>(element::f32, shape_a);
440     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{3}, {2, 3, 6});
441     auto bcast_v3 = make_shared<op::v1::Broadcast>(A, target_shape);
442     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A});
443
444     auto result = make_shared<HostTensor>();
445     ASSERT_TRUE(fun->evaluate(
446         {result}, {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f})}));
447     EXPECT_EQ(result->get_element_type(), element::f32);
448     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
449     auto result_val = read_vector<float>(result);
450     vector<float> expec{
451         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
452         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
453     };
454     ASSERT_EQ(result_val, expec);
455 }
456
457 TEST(eval, evaluate_broadcast_v1_numpy_dyn)
458 {
459     Shape shape_a{3, 1};
460     auto A = make_shared<op::Parameter>(element::f32, shape_a);
461     auto target_shape = make_shared<op::Parameter>(element::i64, Shape{3});
462     auto bcast_v3 = make_shared<op::v1::Broadcast>(A, target_shape);
463     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A, target_shape});
464
465     auto result = make_shared<HostTensor>();
466     ASSERT_TRUE(
467         fun->evaluate({result},
468                       {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f}),
469                        make_host_tensor<element::Type_t::i64>(Shape{3}, {2, 3, 6})}));
470     EXPECT_EQ(result->get_element_type(), element::f32);
471     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
472     auto result_val = read_vector<float>(result);
473     vector<float> expec{
474         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
475         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
476     };
477     ASSERT_EQ(result_val, expec);
478 }
479
480 TEST(eval, evaluate_broadcast_v1_pdpd)
481 {
482     Shape shape_a{3, 1};
483     auto A = make_shared<op::Parameter>(element::f32, shape_a);
484     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{3}, {2, 3, 6});
485     auto bcast_v3 = make_shared<op::v1::Broadcast>(
486         A, target_shape, op::AutoBroadcastSpec(op::AutoBroadcastType::PDPD, 1));
487     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A});
488
489     auto result = make_shared<HostTensor>();
490     ASSERT_TRUE(fun->evaluate(
491         {result}, {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f})}));
492     EXPECT_EQ(result->get_element_type(), element::f32);
493     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
494     auto result_val = read_vector<float>(result);
495     vector<float> expec{
496         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
497         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
498     };
499     ASSERT_EQ(result_val, expec);
500 }
501
502 TEST(eval, evaluate_broadcast_v1_pdpd_dyn)
503 {
504     Shape shape_a{3, 1};
505     auto A = make_shared<op::Parameter>(element::f32, shape_a);
506     auto target_shape = make_shared<op::Parameter>(element::i64, Shape{3});
507     auto bcast_v3 = make_shared<op::v1::Broadcast>(
508         A, target_shape, op::AutoBroadcastSpec(op::AutoBroadcastType::PDPD, 1));
509     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A, target_shape});
510
511     auto result = make_shared<HostTensor>();
512     ASSERT_TRUE(
513         fun->evaluate({result},
514                       {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f}),
515                        make_host_tensor<element::Type_t::i64>(Shape{3}, {2, 3, 6})}));
516     EXPECT_EQ(result->get_element_type(), element::f32);
517     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 6}));
518     auto result_val = read_vector<float>(result);
519     vector<float> expec{
520         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
521         1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3,
522     };
523     ASSERT_EQ(result_val, expec);
524 }
525
526 TEST(eval, evaluate_broadcast_v1_explicit)
527 {
528     Shape shape_a{3, 1};
529     auto A = make_shared<op::Parameter>(element::f32, shape_a);
530     auto target_shape = op::Constant::create<int64_t>(element::i64, Shape{3}, {2, 3, 1});
531     auto axes_mapping = op::Constant::create<int32_t>(element::i32, Shape{2}, {1, 2});
532     auto bcast_v3 = make_shared<op::v1::Broadcast>(
533         A, target_shape, axes_mapping, op::AutoBroadcastSpec(op::AutoBroadcastType::EXPLICIT));
534     auto fun = make_shared<Function>(OutputVector{bcast_v3}, ParameterVector{A});
535
536     auto result = make_shared<HostTensor>();
537     ASSERT_TRUE(fun->evaluate(
538         {result}, {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f})}));
539     EXPECT_EQ(result->get_element_type(), element::f32);
540     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 1}));
541     auto result_val = read_vector<float>(result);
542     vector<float> expec{1, 2, 3, 1, 2, 3};
543     ASSERT_EQ(result_val, expec);
544 }
545
546 TEST(eval, evaluate_broadcast_v1_explicit_dyn)
547 {
548     Shape shape_a{3, 1};
549     auto A = make_shared<op::Parameter>(element::f32, shape_a);
550     auto target_shape = make_shared<op::Parameter>(element::i64, Shape{3});
551     auto axes_mapping = make_shared<op::Parameter>(element::i32, Shape{2});
552
553     auto bcast_v1 = make_shared<op::v1::Broadcast>(
554         A, target_shape, axes_mapping, op::AutoBroadcastSpec(op::AutoBroadcastType::EXPLICIT));
555     auto fun = make_shared<Function>(OutputVector{bcast_v1},
556                                      ParameterVector{A, target_shape, axes_mapping});
557
558     auto result = make_shared<HostTensor>();
559     ASSERT_TRUE(
560         fun->evaluate({result},
561                       {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f}),
562                        make_host_tensor<element::Type_t::i64>(Shape{3}, {2, 3, 1}),
563                        make_host_tensor<element::Type_t::i32>(Shape{2}, {1, 2})}));
564     EXPECT_EQ(result->get_element_type(), element::f32);
565     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 1}));
566     auto result_val = read_vector<float>(result);
567     vector<float> expec{1, 2, 3, 1, 2, 3};
568     ASSERT_EQ(result_val, expec);
569 }
570
571 TEST(eval, evaluate_broadcast_v3_explicit_dyn)
572 {
573     Shape shape_a{3, 1};
574     auto A = make_shared<op::Parameter>(element::f32, shape_a);
575     auto target_shape = make_shared<op::Parameter>(element::i64, Shape{3});
576     auto axes_mapping = make_shared<op::Parameter>(element::i32, Shape{2});
577
578     auto bcast_v3 = make_shared<op::v3::Broadcast>(
579         A, target_shape, axes_mapping, op::BroadcastModeSpec(op::BroadcastType::EXPLICIT));
580     auto fun = make_shared<Function>(OutputVector{bcast_v3},
581                                      ParameterVector{A, target_shape, axes_mapping});
582
583     auto result = make_shared<HostTensor>();
584     ASSERT_TRUE(
585         fun->evaluate({result},
586                       {make_host_tensor<element::Type_t::f32>(Shape{3, 1}, {1.0f, 2.0f, 3.0f}),
587                        make_host_tensor<element::Type_t::i64>(Shape{3}, {2, 3, 1}),
588                        make_host_tensor<element::Type_t::i32>(Shape{2}, {1, 2})}));
589     EXPECT_EQ(result->get_element_type(), element::f32);
590     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3, 1}));
591     auto result_val = read_vector<float>(result);
592     vector<float> expec{1, 2, 3, 1, 2, 3};
593     ASSERT_EQ(result_val, expec);
594 }
595
596 TEST(eval, test_op_multi_out)
597 {
598     auto p = make_shared<op::Parameter>(element::f32, PartialShape{2, 3});
599     auto p2 = make_shared<op::Parameter>(element::f64, PartialShape{2, 2});
600     auto so = make_shared<TestOpMultiOut>(p, p2);
601     auto fun =
602         make_shared<Function>(OutputVector{so->output(0), so->output(1)}, ParameterVector{p, p2});
603     auto result = make_shared<HostTensor>(element::Type_t::f32, Shape{2, 3});
604     auto result2 = make_shared<HostTensor>(element::Type_t::f64, Shape{2, 2});
605     HostTensorVector ins{make_host_tensor<element::Type_t::f32>(Shape{2, 3}),
606                          make_host_tensor<element::Type_t::f64>(Shape{2, 2})};
607     ASSERT_TRUE(fun->evaluate({result, result2}, ins));
608     EXPECT_EQ(result->get_element_type(), element::f32);
609     EXPECT_EQ(result->get_partial_shape(), (PartialShape{2, 3}));
610     auto result_val = read_vector<float>(result);
611     auto arg_val = read_vector<float>(ins[0]);
612     ASSERT_EQ(result_val, arg_val);
613     EXPECT_EQ(result2->get_element_type(), element::f64);
614     EXPECT_EQ(result2->get_partial_shape(), (PartialShape{2, 2}));
615     auto result_val2 = read_vector<double>(result2);
616     auto arg_val2 = read_vector<double>(ins[1]);
617     ASSERT_EQ(result_val2, arg_val2);
618 }
619
620 TEST(eval, evaluate_reshape_v1)
621 {
622     auto data = make_shared<op::Parameter>(element::f32, Shape{2, 5});
623     auto pattern = make_shared<op::Parameter>(element::i64, Shape{2});
624     auto dyn_reshape = make_shared<op::v1::Reshape>(data, pattern, false);
625     auto func = make_shared<Function>(OutputVector{dyn_reshape}, ParameterVector{data, pattern});
626     auto result_tensor = make_shared<HostTensor>();
627     ASSERT_TRUE(func->evaluate(
628         {result_tensor},
629         {make_host_tensor<element::Type_t::f32>({2, 5}, {0, 1, 2, 3, 4, 5, 6, 7, 8, 9}),
630          make_host_tensor<element::Type_t::i64>({2}, {5, 2})}));
631     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
632     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{5, 2}));
633     auto computed_val = read_vector<float>(result_tensor);
634     vector<float> expected_val{0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
635     ASSERT_EQ(computed_val, expected_val);
636 }
637
638 TEST(eval, evaluate_reshape_v1_negative_index)
639 {
640     auto data = make_shared<op::Parameter>(element::f32, Shape{2, 5});
641     auto pattern = make_shared<op::Parameter>(element::i64, Shape{2});
642     auto dyn_reshape = make_shared<op::v1::Reshape>(data, pattern, false);
643     auto func = make_shared<Function>(OutputVector{dyn_reshape}, ParameterVector{data, pattern});
644     auto result_tensor = make_shared<HostTensor>();
645     ASSERT_TRUE(func->evaluate(
646         {result_tensor},
647         {make_host_tensor<element::Type_t::f32>({2, 5}, {0, 1, 2, 3, 4, 5, 6, 7, 8, 9}),
648          make_host_tensor<element::Type_t::i64>({2}, {2, -1})}));
649     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
650     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{2, 5}));
651     auto computed_val = read_vector<float>(result_tensor);
652     vector<float> expected_val{0, 1, 2, 3, 4, 5, 6, 7, 8, 9};
653     ASSERT_EQ(computed_val, expected_val);
654 }
655
656 TEST(eval, evaluate_reshape_v1_negative_index_zero_dim_zero_flag)
657 {
658     auto data = make_shared<op::Parameter>(element::f32, Shape{2, 2, 2, 2});
659     auto pattern = make_shared<op::Parameter>(element::i64, Shape{6});
660     auto dyn_reshape = make_shared<op::v1::Reshape>(data, pattern, true);
661     auto func = make_shared<Function>(OutputVector{dyn_reshape}, ParameterVector{data, pattern});
662     auto result_tensor = make_shared<HostTensor>();
663     ASSERT_TRUE(
664         func->evaluate({result_tensor},
665                        {make_host_tensor<element::Type_t::f32>(
666                             {2, 2, 2, 2}, {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15}),
667                         make_host_tensor<element::Type_t::i64>({6}, {2, 0, 1, -1, 1, 2})}));
668     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
669     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{2, 2, 1, 2, 1, 2}));
670     auto computed_val = read_vector<float>(result_tensor);
671     vector<float> expected_val{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15};
672     ASSERT_EQ(computed_val, expected_val);
673 }
674
675 TEST(eval, evaluate_reshape_v1_pattern_int16)
676 {
677     auto data = make_shared<op::Parameter>(element::f32, Shape{2, 2, 2, 2});
678     auto pattern = make_shared<op::Parameter>(element::i16, Shape{6});
679     auto dyn_reshape = make_shared<op::v1::Reshape>(data, pattern, true);
680     auto func = make_shared<Function>(OutputVector{dyn_reshape}, ParameterVector{data, pattern});
681     auto result_tensor = make_shared<HostTensor>();
682     ASSERT_TRUE(
683         func->evaluate({result_tensor},
684                        {make_host_tensor<element::Type_t::f32>(
685                             {2, 2, 2, 2}, {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15}),
686                         make_host_tensor<element::Type_t::i16>({6}, {2, 0, 1, -1, 1, 2})}));
687     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
688     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{2, 2, 1, 2, 1, 2}));
689     auto computed_val = read_vector<float>(result_tensor);
690     vector<float> expected_val{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15};
691     ASSERT_EQ(computed_val, expected_val);
692 }
693
694 TEST(eval, evaluate_convert)
695 {
696     auto p = make_shared<op::Parameter>(element::f32, PartialShape{-1, -1});
697     auto convert = make_shared<op::v0::Convert>(p, element::i64);
698     auto fun = make_shared<Function>(OutputVector{convert}, ParameterVector{p});
699
700     std::vector<std::vector<float>> inputs{{-1, 1}};
701     std::vector<std::vector<int64_t>> expected_result{{-1, 1}};
702     for (size_t i = 0; i < inputs.size(); i++)
703     {
704         auto result = make_shared<HostTensor>();
705         ASSERT_TRUE(fun->evaluate(
706             {result}, {make_host_tensor<element::Type_t::f32>(Shape{1, 2}, inputs[i])}));
707         EXPECT_EQ(result->get_element_type(), element::i64);
708         EXPECT_EQ(result->get_shape(), (Shape{1, 2}));
709         auto result_data = read_vector<int64_t>(result);
710         ASSERT_EQ(result_data, expected_result[i]);
711     }
712 }
713
714 TEST(eval, evaluate_abs)
715 {
716     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 3});
717     auto abs = make_shared<op::Abs>(p);
718     auto fun = make_shared<Function>(OutputVector{abs}, ParameterVector{p});
719     auto result = make_shared<HostTensor>();
720     ASSERT_TRUE(fun->evaluate({result},
721                               {make_host_tensor<element::Type_t::f32>(
722                                   Shape{2, 3}, {0.0f, -1.0f, -2.0f, -3.0f, 4.0f, 5.0f})}));
723     EXPECT_EQ(result->get_element_type(), element::f32);
724     auto result_val = read_vector<float>(result);
725     vector<float> expec{0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f};
726     ASSERT_EQ(result_val, expec);
727 }
728
729 TEST(eval, evaluate_erf)
730 {
731     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 3});
732     auto erf = make_shared<op::Erf>(p);
733     auto fun = make_shared<Function>(OutputVector{erf}, ParameterVector{p});
734     auto result = make_shared<HostTensor>();
735     ASSERT_TRUE(fun->evaluate({result},
736                               {make_host_tensor<element::Type_t::f32>(
737                                   Shape{2, 3}, {0.0f, -1.0f, -2.0f, -3.0f, 4.0f, 5.0f})}));
738     EXPECT_EQ(result->get_element_type(), element::f32);
739     auto result_val = read_vector<float>(result);
740     vector<float> expec{std::erf(0.0f),
741                         std::erf(-1.0f),
742                         std::erf(-2.0f),
743                         std::erf(-3.0f),
744                         std::erf(4.0f),
745                         std::erf(5.0f)};
746     ASSERT_EQ(result_val, expec);
747 }
748
749 TEST(eval, evaluate_exp)
750 {
751     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 3});
752     auto exp = make_shared<op::Exp>(p);
753     auto fun = make_shared<Function>(OutputVector{exp}, ParameterVector{p});
754     auto result = make_shared<HostTensor>();
755     ASSERT_TRUE(fun->evaluate({result},
756                               {make_host_tensor<element::Type_t::f32>(
757                                   Shape{2, 3}, {0.0f, -1.0f, -2.0f, -3.0f, 4.0f, 5.0f})}));
758     EXPECT_EQ(result->get_element_type(), element::f32);
759     auto result_val = read_vector<float>(result);
760     vector<float> expec{std::exp(0.0f),
761                         std::exp(-1.0f),
762                         std::exp(-2.0f),
763                         std::exp(-3.0f),
764                         std::exp(4.0f),
765                         std::exp(5.0f)};
766     ASSERT_FLOAT_VECTORS_EQ(expec, result_val);
767 }
768
769 TEST(eval, evaluate_floor)
770 {
771     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 2});
772     auto floor = make_shared<op::Floor>(p);
773     auto fun = make_shared<Function>(OutputVector{floor}, ParameterVector{p});
774     auto result = make_shared<HostTensor>();
775     ASSERT_TRUE(fun->evaluate(
776         {result},
777         {make_host_tensor<element::Type_t::f32>(Shape{2, 2}, {-2.5f, -2.0f, 0.3f, 4.8f})}));
778     EXPECT_EQ(result->get_element_type(), element::f32);
779     auto result_val = read_vector<float>(result);
780     vector<float> expec{-3.0f, -2.0f, 0.0f, 4.0f};
781     ASSERT_EQ(result_val, expec);
782 }
783
784 TEST(eval, evaluate_floor_int32)
785 {
786     auto p = make_shared<op::Parameter>(element::i32, Shape{2, 2});
787     auto floor = make_shared<op::Floor>(p);
788     auto fun = make_shared<Function>(OutputVector{floor}, ParameterVector{p});
789     auto result = make_shared<HostTensor>();
790     ASSERT_TRUE(fun->evaluate({result},
791                               {make_host_tensor<element::Type_t::i32>(
792                                   Shape{2, 2}, {-2, -136314888, 0x40000010, 0x40000001})}));
793     EXPECT_EQ(result->get_element_type(), element::i32);
794     auto result_val = read_vector<int32_t>(result);
795     vector<int32_t> expec{-2, -136314888, 0x40000010, 0x40000001};
796     ASSERT_EQ(result_val, expec);
797 }
798
799 TEST(eval, evaluate_log)
800 {
801     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 2, 2});
802     auto log = make_shared<op::Log>(p);
803     auto fun = make_shared<Function>(OutputVector{log}, ParameterVector{p});
804     auto result = make_shared<HostTensor>();
805     ASSERT_TRUE(
806         fun->evaluate({result},
807                       {make_host_tensor<element::Type_t::f32>(
808                           Shape{2, 2, 2}, {0.125f, 0.25f, 0.5f, 1.f, 2.f, 4.f, 8.f, 16.f})}));
809     EXPECT_EQ(result->get_element_type(), element::f32);
810     auto result_val = read_vector<float>(result);
811     vector<float> expec{std::log(0.125f),
812                         std::log(0.25f),
813                         std::log(0.5f),
814                         std::log(1.f),
815                         std::log(2.f),
816                         std::log(4.f),
817                         std::log(8.f),
818                         std::log(16.f)};
819     ASSERT_EQ(result_val, expec);
820 }
821
822 TEST(eval, evaluate_negative_f32)
823 {
824     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 5});
825     auto negate = make_shared<op::Negative>(p);
826     auto fun = make_shared<Function>(OutputVector{negate}, ParameterVector{p});
827     auto result = make_shared<HostTensor>();
828     ASSERT_TRUE(fun->evaluate(
829         {result},
830         {make_host_tensor<element::Type_t::f32>(
831             Shape{2, 5},
832             {1.35f, 8.76f, -8.0f, 17.234f, -2.121f, 1.0f, 8.7f, -8.92f, 17.0f, -1.0f})}));
833     EXPECT_EQ(result->get_element_type(), element::f32);
834     auto result_val = read_vector<float>(result);
835     vector<float> expec{-1.35f, -8.76f, 8.0f, -17.234f, 2.121f, -1.0f, -8.7f, 8.92f, -17.0f, 1.0f};
836     ASSERT_EQ(result_val, expec);
837 }
838
839 TEST(eval, evaluate_negative_i32)
840 {
841     auto p = make_shared<op::Parameter>(element::i32, Shape{2, 5});
842     auto negate = make_shared<op::Negative>(p);
843     auto fun = make_shared<Function>(OutputVector{negate}, ParameterVector{p});
844     auto result = make_shared<HostTensor>();
845     ASSERT_TRUE(fun->evaluate({result},
846                               {make_host_tensor<element::Type_t::i32>(
847                                   Shape{2, 5}, {1, 8, -8, 17, -2, 1, 8, -8, 17, 0})}));
848     EXPECT_EQ(result->get_element_type(), element::i32);
849     auto result_val = read_vector<int32_t>(result);
850     vector<int32_t> expec{-1, -8, 8, -17, 2, -1, -8, 8, -17, 0};
851     ASSERT_EQ(result_val, expec);
852 }
853
854 TEST(eval, evaluate_relu_2Ffprop_f32)
855 {
856     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 5});
857     auto relu = make_shared<op::Relu>(p);
858     auto fun = make_shared<Function>(OutputVector{relu}, ParameterVector{p});
859     auto result = make_shared<HostTensor>();
860     ASSERT_TRUE(fun->evaluate({result},
861                               {make_host_tensor<element::Type_t::f32>(
862                                   Shape{2, 5}, {1, 8, -8, 17, -0.5, 0.1, 8.5, -8, 17, -0.5})}));
863     EXPECT_EQ(result->get_element_type(), element::f32);
864     auto result_val = read_vector<float>(result);
865     vector<float> expec{1, 8, 0, 17, 0, 0.1, 8.5, 0, 17, 0};
866     ASSERT_EQ(result_val, expec);
867 }
868
869 TEST(eval, evaluate_relu_2Ffprop_i32)
870 {
871     auto p = make_shared<op::Parameter>(element::i32, Shape{2, 5});
872     auto relu = make_shared<op::Relu>(p);
873     auto fun = make_shared<Function>(OutputVector{relu}, ParameterVector{p});
874     auto result = make_shared<HostTensor>();
875     ASSERT_TRUE(fun->evaluate({result},
876                               {make_host_tensor<element::Type_t::i32>(
877                                   Shape{2, 5}, {1, 8, -8, 17, -2, 1, 8, -8, 17, -1})}));
878     EXPECT_EQ(result->get_element_type(), element::i32);
879     auto result_val = read_vector<int32_t>(result);
880     vector<int32_t> expec{1, 8, 0, 17, 0, 1, 8, 0, 17, 0};
881     ASSERT_EQ(result_val, expec);
882 }
883
884 TEST(eval, evaluate_round)
885 {
886     auto p = make_shared<op::Parameter>(element::f32, Shape{5});
887     auto round = make_shared<op::Round>(p);
888     auto fun = make_shared<Function>(OutputVector{round}, ParameterVector{p});
889     auto result = make_shared<HostTensor>();
890     ASSERT_TRUE(fun->evaluate(
891         {result},
892         {make_host_tensor<element::Type_t::f32>(Shape{5}, {0.9f, 2.5f, 2.3f, 1.5f, -4.5f})}));
893     EXPECT_EQ(result->get_element_type(), element::f32);
894     auto result_val = read_vector<float>(result);
895     vector<float> expec{1.0f, 2.0f, 2.0f, 2.0f, -4.0f};
896     ASSERT_EQ(result_val, expec);
897 }
898
899 TEST(eval, evaluate_round_2D)
900 {
901     auto p = make_shared<op::Parameter>(element::f32, Shape{3, 5});
902     auto round = make_shared<op::Round>(p);
903     auto fun = make_shared<Function>(OutputVector{round}, ParameterVector{p});
904     auto result = make_shared<HostTensor>();
905     ASSERT_TRUE(fun->evaluate({result},
906                               {make_host_tensor<element::Type_t::f32>(Shape{3, 5},
907                                                                       {0.1f,
908                                                                        0.5f,
909                                                                        0.9f,
910                                                                        1.2f,
911                                                                        1.5f,
912                                                                        1.8f,
913                                                                        2.3f,
914                                                                        2.5f,
915                                                                        2.7f,
916                                                                        -1.1f,
917                                                                        -1.5f,
918                                                                        -1.9f,
919                                                                        -2.2f,
920                                                                        -2.5f,
921                                                                        -2.8f})}));
922     EXPECT_EQ(result->get_element_type(), element::f32);
923     auto result_val = read_vector<float>(result);
924     vector<float> expec{
925         0.f, 0.f, 1.f, 1.f, 2.f, 2.f, 2.f, 2.f, 3.f, -1.f, -2.f, -2.f, -2.f, -2.f, -3.f};
926     ASSERT_EQ(result_val, expec);
927 }
928
929 TEST(eval, evaluate_sigmoid)
930 {
931     auto p = make_shared<op::Parameter>(element::f32, Shape{1, 1, 2, 2});
932     auto sigmoid = make_shared<op::Sigmoid>(p);
933     auto fun = make_shared<Function>(OutputVector{sigmoid}, ParameterVector{p});
934     auto result = make_shared<HostTensor>();
935
936     float x1 = 1.0f;
937     float x2 = 4.0f;
938     float sigma1 = 1.0f / (1.0f + std::exp(-x1));
939     float sigma2 = 1.0f / (1.0f + std::exp(-x2));
940     ASSERT_TRUE(fun->evaluate(
941         {result}, {make_host_tensor<element::Type_t::f32>(Shape{1, 1, 2, 2}, {x1, x2, x1, x2})}));
942     EXPECT_EQ(result->get_element_type(), element::f32);
943     auto result_val = read_vector<float>(result);
944     vector<float> expec{sigma1, sigma2, sigma1, sigma2};
945     EXPECT_EQ(result_val.size(), expec.size());
946 }
947
948 TEST(eval, evaluate_sign)
949 {
950     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 3});
951     auto sign = make_shared<op::Sign>(p);
952     auto fun = make_shared<Function>(OutputVector{sign}, ParameterVector{p});
953     auto result = make_shared<HostTensor>();
954
955     ASSERT_TRUE(fun->evaluate(
956         {result},
957         {make_host_tensor<element::Type_t::f32>(Shape{2, 3}, {1, -2, 0, -4.8f, 4.8f, -0.0f})}));
958     EXPECT_EQ(result->get_element_type(), element::f32);
959     auto result_val = read_vector<float>(result);
960     vector<float> expec{1, -1, 0, -1, 1, 0};
961     ASSERT_EQ(result_val, expec);
962 }
963
964 TEST(eval, evaluate_sin)
965 {
966     auto p = make_shared<op::Parameter>(element::f32, Shape{11});
967     auto sin = make_shared<op::Sin>(p);
968     auto fun = make_shared<Function>(OutputVector{sin}, ParameterVector{p});
969     auto result = make_shared<HostTensor>();
970
971     ASSERT_TRUE(fun->evaluate(
972         {result},
973         {make_host_tensor<element::Type_t::f32>(
974             Shape{11}, {0.f, 0.25f, -0.25f, 0.5f, -0.5f, 1.f, -1.f, 2.f, -2.f, 4.f, -4.f})}));
975     EXPECT_EQ(result->get_element_type(), element::f32);
976     auto result_val = read_vector<float>(result);
977     vector<float> expec{0.00000000f,
978                         0.24740396f,
979                         -0.24740396f,
980                         0.47942554f,
981                         -0.47942554f,
982                         0.84147098f,
983                         -0.84147098f,
984                         0.90929743f,
985                         -0.90929743f,
986                         -0.75680250f,
987                         0.75680250f};
988     ASSERT_FLOAT_VECTORS_EQ(expec, result_val);
989 }
990
991 TEST(eval, evaluate_sinh)
992 {
993     auto p = make_shared<op::Parameter>(element::f32, Shape{6});
994     auto sinh = make_shared<op::Sinh>(p);
995     auto fun = make_shared<Function>(OutputVector{sinh}, ParameterVector{p});
996     auto result = make_shared<HostTensor>();
997
998     vector<float> input{1.0f, 0.0f, -0.0f, -1.0f, 5.0f, -5.0f};
999     ASSERT_TRUE(fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{6}, input)}));
1000     EXPECT_EQ(result->get_element_type(), element::f32);
1001     auto result_val = read_vector<float>(result);
1002     std::transform(
1003         input.begin(), input.end(), input.begin(), [](float x) -> float { return sinhf(x); });
1004     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1005 }
1006
1007 TEST(eval, evaluate_sqrt)
1008 {
1009     auto p = make_shared<op::Parameter>(element::f32, Shape{6});
1010     auto sqrt = make_shared<op::Sqrt>(p);
1011     auto fun = make_shared<Function>(OutputVector{sqrt}, ParameterVector{p});
1012     auto result = make_shared<HostTensor>();
1013
1014     vector<float> input{16, 4, 81, 100, 10000, 0};
1015     ASSERT_TRUE(fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{6}, input)}));
1016     EXPECT_EQ(result->get_element_type(), element::f32);
1017     auto result_val = read_vector<float>(result);
1018     vector<float> expec{4, 2, 9, 10, 100, 0};
1019     ASSERT_FLOAT_VECTORS_EQ(expec, result_val);
1020 }
1021
1022 TEST(eval, evaluate_acos)
1023 {
1024     auto p = make_shared<op::Parameter>(element::f32, Shape{11});
1025     auto acos = make_shared<op::Acos>(p);
1026     auto fun = make_shared<Function>(OutputVector{acos}, ParameterVector{p});
1027     auto result = make_shared<HostTensor>();
1028
1029     vector<float> input{-1.f, -0.75f, -0.5f, -0.25f, -0.125f, 0.f, 0.125f, 0.25f, 0.5f, 0.75f, 1.f};
1030     ASSERT_TRUE(
1031         fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{11}, input)}));
1032     EXPECT_EQ(result->get_element_type(), element::f32);
1033     auto result_val = read_vector<float>(result);
1034     std::transform(
1035         input.begin(), input.end(), input.begin(), [](float x) -> float { return std::acos(x); });
1036     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1037 }
1038
1039 TEST(eval, evaluate_asin)
1040 {
1041     auto p = make_shared<op::Parameter>(element::f32, Shape{11});
1042     auto asin = make_shared<op::Asin>(p);
1043     auto fun = make_shared<Function>(OutputVector{asin}, ParameterVector{p});
1044     auto result = make_shared<HostTensor>();
1045
1046     vector<float> input{-1.f, -0.75f, -0.5f, -0.25f, -0.125f, 0.f, 0.125f, 0.25f, 0.5f, 0.75f, 1.f};
1047     ASSERT_TRUE(
1048         fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{11}, input)}));
1049     EXPECT_EQ(result->get_element_type(), element::f32);
1050     auto result_val = read_vector<float>(result);
1051     std::transform(
1052         input.begin(), input.end(), input.begin(), [](float x) -> float { return std::asin(x); });
1053
1054     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1055 }
1056
1057 TEST(eval, evaluate_atan)
1058 {
1059     auto p = make_shared<op::Parameter>(element::f32, Shape{11});
1060     auto atan = make_shared<op::Atan>(p);
1061     auto fun = make_shared<Function>(OutputVector{atan}, ParameterVector{p});
1062     auto result = make_shared<HostTensor>();
1063
1064     vector<float> input{-4.f, -2.f, -1.f, -0.5f, -0.25f, 0.f, 0.25f, 0.5f, 1.f, 2.f, 4.f};
1065     ASSERT_TRUE(
1066         fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{11}, input)}));
1067     EXPECT_EQ(result->get_element_type(), element::f32);
1068     auto result_val = read_vector<float>(result);
1069     std::transform(
1070         input.begin(), input.end(), input.begin(), [](float x) -> float { return std::atan(x); });
1071
1072     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1073 }
1074
1075 TEST(eval, evaluate_ceiling)
1076 {
1077     auto p = make_shared<op::Parameter>(element::f32, Shape{2, 2});
1078     auto ceil = make_shared<op::Ceiling>(p);
1079     auto fun = make_shared<Function>(OutputVector{ceil}, ParameterVector{p});
1080     auto result = make_shared<HostTensor>();
1081
1082     vector<float> input{-2.5f, -2.0f, 0.3f, 4.8f};
1083     ASSERT_TRUE(
1084         fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{2, 2}, input)}));
1085     EXPECT_EQ(result->get_element_type(), element::f32);
1086     auto result_val = read_vector<float>(result);
1087     vector<float> expec{-2.0f, -2.0f, 1.0f, 5.0f};
1088     ASSERT_EQ(result_val, expec);
1089 }
1090
1091 TEST(eval, evaluate_cos)
1092 {
1093     auto p = make_shared<op::Parameter>(element::f32, Shape{11});
1094     auto cos = make_shared<op::Cos>(p);
1095     auto fun = make_shared<Function>(OutputVector{cos}, ParameterVector{p});
1096     auto result = make_shared<HostTensor>();
1097
1098     vector<float> input{0.f, 0.25f, -0.25f, 0.5f, -0.5f, 1.f, -1.f, 2.f, -2.f, 4.f, -4.f};
1099     ASSERT_TRUE(
1100         fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{11}, input)}));
1101     EXPECT_EQ(result->get_element_type(), element::f32);
1102     auto result_val = read_vector<float>(result);
1103     std::transform(
1104         input.begin(), input.end(), input.begin(), [](float x) -> float { return std::cos(x); });
1105
1106     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1107 }
1108
1109 TEST(eval, evaluate_cosh)
1110 {
1111     auto p = make_shared<op::Parameter>(element::f32, Shape{6});
1112     auto cosh = make_shared<op::Cosh>(p);
1113     auto fun = make_shared<Function>(OutputVector{cosh}, ParameterVector{p});
1114     auto result = make_shared<HostTensor>();
1115
1116     vector<float> input{1.0f, 0.0f, -0.0f, -1.0f, 5.0f, -5.0f};
1117     ASSERT_TRUE(fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{6}, input)}));
1118     EXPECT_EQ(result->get_element_type(), element::f32);
1119     auto result_val = read_vector<float>(result);
1120     std::transform(
1121         input.begin(), input.end(), input.begin(), [](float x) -> float { return std::cosh(x); });
1122
1123     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1124 }
1125
1126 TEST(eval, evaluate_tan)
1127 {
1128     auto p = make_shared<op::Parameter>(element::f32, Shape{11});
1129     auto tan = make_shared<op::Tan>(p);
1130     auto fun = make_shared<Function>(OutputVector{tan}, ParameterVector{p});
1131     auto result = make_shared<HostTensor>();
1132
1133     vector<float> input{0.f, 0.25f, -0.25f, 0.5f, -0.5f, 1.f, -1.f, 2.f, -2.f, 4.f, -4.f};
1134     ASSERT_TRUE(
1135         fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{11}, input)}));
1136     EXPECT_EQ(result->get_element_type(), element::f32);
1137     auto result_val = read_vector<float>(result);
1138     std::transform(
1139         input.begin(), input.end(), input.begin(), [](float x) -> float { return std::tan(x); });
1140
1141     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1142 }
1143
1144 TEST(eval, evaluate_tanh)
1145 {
1146     auto p = make_shared<op::Parameter>(element::f32, Shape{6});
1147     auto tanh = make_shared<op::Tanh>(p);
1148     auto fun = make_shared<Function>(OutputVector{tanh}, ParameterVector{p});
1149     auto result = make_shared<HostTensor>();
1150
1151     vector<float> input{1.0f, 0.0f, -0.0f, -1.0f, 0.5f, -0.5f};
1152     ASSERT_TRUE(fun->evaluate({result}, {make_host_tensor<element::Type_t::f32>(Shape{6}, input)}));
1153     EXPECT_EQ(result->get_element_type(), element::f32);
1154     auto result_val = read_vector<float>(result);
1155     std::transform(
1156         input.begin(), input.end(), input.begin(), [](float x) -> float { return std::tanh(x); });
1157
1158     ASSERT_FLOAT_VECTORS_EQ(input, result_val);
1159 }
1160
1161 TEST(eval, evaluate_not)
1162 {
1163     auto p = make_shared<op::Parameter>(element::boolean, Shape{2, 2});
1164     auto op_not = make_shared<op::Not>(p);
1165     auto fun = make_shared<Function>(OutputVector{op_not}, ParameterVector{p});
1166     auto result = make_shared<HostTensor>();
1167
1168     ASSERT_TRUE(fun->evaluate(
1169         {result}, {make_host_tensor<element::Type_t::boolean>(Shape{2, 2}, {1, 0, 1, 0})}));
1170     EXPECT_EQ(result->get_element_type(), element::boolean);
1171     auto result_val = read_vector<char>(result);
1172     vector<char> expec{0, 1, 0, 1};
1173     ASSERT_EQ(result_val, expec);
1174 }
1175
1176 TEST(eval, evaluate_not_i32)
1177 {
1178     auto p = make_shared<op::Parameter>(element::i32, Shape{2, 2});
1179     auto op_not = make_shared<op::Not>(p);
1180     auto fun = make_shared<Function>(OutputVector{op_not}, ParameterVector{p});
1181     auto result = make_shared<HostTensor>();
1182
1183     ASSERT_TRUE(fun->evaluate(
1184         {result}, {make_host_tensor<element::Type_t::i32>(Shape{2, 2}, {100, 0, -2, 0})}));
1185     EXPECT_EQ(result->get_element_type(), element::i32);
1186     auto result_val = read_vector<int32_t>(result);
1187     vector<int32_t> expec{0, 1, 0, 1};
1188     ASSERT_EQ(result_val, expec);
1189 }
1190
1191 TEST(eval, evaluate_logical_not)
1192 {
1193     auto p = make_shared<op::Parameter>(element::boolean, Shape{2, 2});
1194     auto logical_not = make_shared<op::v1::LogicalNot>(p);
1195     auto fun = make_shared<Function>(OutputVector{logical_not}, ParameterVector{p});
1196     auto result = make_shared<HostTensor>();
1197
1198     ASSERT_TRUE(fun->evaluate(
1199         {result}, {make_host_tensor<element::Type_t::boolean>(Shape{2, 2}, {1, 0, 1, 0})}));
1200     EXPECT_EQ(result->get_element_type(), element::boolean);
1201     auto result_val = read_vector<char>(result);
1202     vector<char> expec{0, 1, 0, 1};
1203     ASSERT_EQ(result_val, expec);
1204 }
1205
1206 TEST(eval, evaluate_dynamic_gather)
1207 {
1208     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1209     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1210     auto gather = make_shared<op::v0::Gather>(arg1, arg2);
1211     auto fun = make_shared<Function>(OutputVector{gather}, ParameterVector{arg1, arg2});
1212     auto result_tensor = make_shared<HostTensor>();
1213     ASSERT_TRUE(fun->evaluate({result_tensor},
1214                               {make_host_tensor<element::Type_t::f32>({3}, {1.0f, 2.0f, 3.0f}),
1215                                make_host_tensor<element::Type_t::i32>({2}, {1, 0})}));
1216     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1217     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{2}));
1218     auto cval = read_vector<float>(result_tensor);
1219     vector<float> out{2.0f, 1.0f};
1220     ASSERT_EQ(cval, out);
1221 }
1222
1223 TEST(eval, evaluate_dynamic_axis_gather)
1224 {
1225     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1226     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1227     auto arg3 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
1228     auto gather = make_shared<op::v1::Gather>(arg1, arg2, arg3);
1229     auto fun = make_shared<Function>(OutputVector{gather}, ParameterVector{arg1, arg2, arg3});
1230     auto result_tensor = make_shared<HostTensor>();
1231     ASSERT_TRUE(fun->evaluate({result_tensor},
1232                               {make_host_tensor<element::Type_t::f32>(
1233                                    {3, 3}, {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f, 3.0f, 3.1f, 3.2f}),
1234                                make_host_tensor<element::Type_t::i32>({1, 2}, {0, 2}),
1235                                make_host_tensor<element::Type_t::u64>({}, {1})}));
1236     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1237     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 1, 2}));
1238     auto cval = read_vector<float>(result_tensor);
1239     vector<float> out{1.0f, 1.2f, 2.0f, 2.2f, 3.0f, 3.2f};
1240     ASSERT_EQ(cval, out);
1241 }
1242
1243 TEST(eval, evaluate_dynamic_concat)
1244 {
1245     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1246     auto arg2 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1247     auto concat = make_shared<op::v0::Concat>(NodeVector{arg1, arg2}, 1);
1248     auto fun = make_shared<Function>(OutputVector{concat}, ParameterVector{arg1, arg2});
1249     auto result_tensor = make_shared<HostTensor>();
1250     ASSERT_TRUE(fun->evaluate({result_tensor},
1251                               {make_host_tensor<element::Type_t::f32>({1, 1}, {1.0f}),
1252                                make_host_tensor<element::Type_t::f32>({1, 2}, {8.0f, 10.0f})}));
1253     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1254     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{1, 3}));
1255     auto cval = read_vector<float>(result_tensor);
1256     vector<float> out{1.0f, 8.0f, 10.0f};
1257     ASSERT_EQ(cval, out);
1258 }
1259
1260 template <element::Type_t T>
1261 void test_eval(shared_ptr<Function> fun,
1262                vector<vector<float>>& inputs,
1263                vector<Shape>& x_shapes,
1264                vector<Shape>& result_shapes,
1265                vector<vector<float>>& results)
1266 {
1267     using IN_T = typename element_type_traits<T>::value_type;
1268     std::vector<std::vector<IN_T>> perms{{0, 1}, {1, 0}, {2, 1, 0}};
1269     for (size_t i = 0; i < x_shapes.size(); i++)
1270     {
1271         auto result_tensor = make_shared<HostTensor>();
1272         ASSERT_TRUE(fun->evaluate({result_tensor},
1273                                   {make_host_tensor<element::Type_t::f32>(x_shapes[i], inputs[i]),
1274                                    make_host_tensor<T>(Shape{perms[i].size()}, perms[i])}));
1275
1276         ASSERT_EQ(result_tensor->get_shape(), result_shapes[i]);
1277         auto actual_results = read_vector<float>(result_tensor);
1278         ASSERT_EQ(actual_results, results[i]);
1279     }
1280 }
1281
1282 TEST(eval, eval_transpose)
1283 {
1284     auto x = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1285     vector<shared_ptr<op::Parameter>> axes;
1286     axes.push_back(make_shared<op::Parameter>(element::i8, PartialShape{Dimension::dynamic()}));
1287     axes.push_back(make_shared<op::Parameter>(element::i16, PartialShape{Dimension::dynamic()}));
1288     axes.push_back(make_shared<op::Parameter>(element::i32, PartialShape{Dimension::dynamic()}));
1289     axes.push_back(make_shared<op::Parameter>(element::i64, PartialShape{Dimension::dynamic()}));
1290
1291     axes.push_back(make_shared<op::Parameter>(element::u8, PartialShape{Dimension::dynamic()}));
1292     axes.push_back(make_shared<op::Parameter>(element::u16, PartialShape{Dimension::dynamic()}));
1293     axes.push_back(make_shared<op::Parameter>(element::u32, PartialShape{Dimension::dynamic()}));
1294     axes.push_back(make_shared<op::Parameter>(element::u64, PartialShape{Dimension::dynamic()}));
1295
1296     std::vector<Shape> x_shapes{Shape{2, 3}, Shape{2, 3}, Shape{2, 2, 3}};
1297
1298     std::vector<std::vector<float>> inputs{
1299         {1, 2, 3, 4, 5, 6}, {1, 2, 3, 4, 5, 6}, {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12}};
1300     std::vector<Shape> result_shapes{Shape{2, 3}, Shape{3, 2}, {3, 2, 2}};
1301     std::vector<std::vector<float>> results{
1302         {1, 2, 3, 4, 5, 6}, {1, 4, 2, 5, 3, 6}, {1, 7, 4, 10, 2, 8, 5, 11, 3, 9, 6, 12}};
1303
1304     for (auto& axis : axes)
1305     {
1306         auto x_transpose = make_shared<op::v1::Transpose>(x, axis);
1307         auto fun = make_shared<Function>(NodeVector{x_transpose}, ParameterVector{x, axis});
1308
1309         switch (axis->get_element_type())
1310         {
1311         case element::Type_t::i8:
1312             test_eval<element::Type_t::i8>(fun, inputs, x_shapes, result_shapes, results);
1313             break;
1314         case element::Type_t::i16:
1315             test_eval<element::Type_t::i16>(fun, inputs, x_shapes, result_shapes, results);
1316             break;
1317         case element::Type_t::i32:
1318             test_eval<element::Type_t::i32>(fun, inputs, x_shapes, result_shapes, results);
1319             break;
1320         case element::Type_t::i64:
1321             test_eval<element::Type_t::i64>(fun, inputs, x_shapes, result_shapes, results);
1322             break;
1323         case element::Type_t::u8:
1324             test_eval<element::Type_t::u8>(fun, inputs, x_shapes, result_shapes, results);
1325             break;
1326         case element::Type_t::u16:
1327             test_eval<element::Type_t::u16>(fun, inputs, x_shapes, result_shapes, results);
1328             break;
1329         case element::Type_t::u32:
1330             test_eval<element::Type_t::u32>(fun, inputs, x_shapes, result_shapes, results);
1331             break;
1332         case element::Type_t::u64:
1333             test_eval<element::Type_t::u64>(fun, inputs, x_shapes, result_shapes, results);
1334             break;
1335         default: NGRAPH_CHECK(false, "Invalid type"); break;
1336         }
1337     }
1338 }
1339
1340 TEST(eval, max_pool_v1_dynamic)
1341 {
1342     Shape window_shape{3};
1343     auto A = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1344     auto f = make_shared<Function>(
1345         make_shared<op::v1::MaxPool>(
1346             A, Strides(), Shape(), Shape(), window_shape, op::RoundingType::FLOOR),
1347         ParameterVector{A});
1348     auto result_tensor = make_shared<HostTensor>();
1349
1350     ASSERT_TRUE(f->evaluate({result_tensor},
1351                             {make_host_tensor<element::Type_t::f32>(
1352                                 {1, 1, 14}, {0, 1, 0, 2, 1, 0, 3, 2, 0, 0, 2, 0, 0, 0})}));
1353
1354     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1355     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{1, 1, 12}));
1356     auto cval = read_vector<float>(result_tensor);
1357     vector<float> out{1, 2, 2, 2, 3, 3, 3, 2, 2, 2, 2, 0};
1358 }
1359
1360 TEST(eval, evaluate_static_scatter_elements_update_basic)
1361 {
1362     const Shape data_shape{3, 3};
1363     const Shape indices_shape{2, 3};
1364     auto arg1 = make_shared<op::Parameter>(element::f32, data_shape);
1365     auto arg2 = make_shared<op::Parameter>(element::i32, indices_shape);
1366     auto arg3 = make_shared<op::Parameter>(element::f32, indices_shape);
1367     auto arg4 = make_shared<op::Parameter>(element::i64, Shape{});
1368     auto scatter_elements_update =
1369         make_shared<op::v3::ScatterElementsUpdate>(arg1, arg2, arg3, arg4);
1370     auto fun = make_shared<Function>(OutputVector{scatter_elements_update},
1371                                      ParameterVector{arg1, arg2, arg3, arg4});
1372     auto result_tensor = make_shared<HostTensor>();
1373     ASSERT_TRUE(
1374         fun->evaluate({result_tensor},
1375                       {make_host_tensor<element::Type_t::f32>(
1376                            data_shape, {0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f}),
1377                        make_host_tensor<element::Type_t::i32>(indices_shape, {1, 0, 2, 0, 2, 1}),
1378                        make_host_tensor<element::Type_t::f32>(indices_shape,
1379                                                               {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
1380                        make_host_tensor<element::Type_t::i64>({}, {0})}));
1381     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1382     EXPECT_EQ(result_tensor->get_shape(), (Shape{3, 3}));
1383     auto cval = read_vector<float>(result_tensor);
1384     vector<float> out{2.f, 1.1f, 0.0f, 1.f, 0.0f, 2.2f, 0.f, 2.1f, 1.2f};
1385     ASSERT_EQ(cval, out);
1386 }
1387
1388 TEST(eval, evaluate_dynamic_scatter_elements_update_basic)
1389 {
1390     const Shape data_shape{3, 3};
1391     const Shape indices_shape{2, 3};
1392
1393     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1394     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1395     auto arg3 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1396     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
1397
1398     auto scatter_elements_update =
1399         make_shared<op::v3::ScatterElementsUpdate>(arg1, arg2, arg3, arg4);
1400     auto fun = make_shared<Function>(OutputVector{scatter_elements_update},
1401                                      ParameterVector{arg1, arg2, arg3, arg4});
1402     auto result_tensor = make_shared<HostTensor>();
1403     ASSERT_TRUE(
1404         fun->evaluate({result_tensor},
1405                       {make_host_tensor<element::Type_t::f32>(
1406                            data_shape, {0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f}),
1407                        make_host_tensor<element::Type_t::i32>(indices_shape, {1, 0, 2, 0, 2, 1}),
1408                        make_host_tensor<element::Type_t::f32>(indices_shape,
1409                                                               {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
1410                        make_host_tensor<element::Type_t::i64>({}, {0})}));
1411
1412     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1413     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3}));
1414     auto cval = read_vector<float>(result_tensor);
1415     vector<float> out{2.f, 1.1f, 0.0f, 1.f, 0.0f, 2.2f, 0.f, 2.1f, 1.2f};
1416     ASSERT_EQ(cval, out);
1417 }
1418
1419 TEST(eval, evaluate_dynamic_scatter_elements_update_negative_axis)
1420 {
1421     const Shape data_shape{3, 3};
1422     const Shape indices_shape{2, 3};
1423     const Shape axis_shape{};
1424
1425     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1426     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1427     auto arg3 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1428     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
1429
1430     auto scatter_elements_update =
1431         make_shared<op::v3::ScatterElementsUpdate>(arg1, arg2, arg3, arg4);
1432     auto fun = make_shared<Function>(OutputVector{scatter_elements_update},
1433                                      ParameterVector{arg1, arg2, arg3, arg4});
1434     auto result_tensor = make_shared<HostTensor>();
1435     ASSERT_TRUE(
1436         fun->evaluate({result_tensor},
1437                       {make_host_tensor<element::Type_t::f32>(
1438                            data_shape, {0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f}),
1439                        make_host_tensor<element::Type_t::i32>(indices_shape, {1, 0, 2, 0, 2, 1}),
1440                        make_host_tensor<element::Type_t::f32>(indices_shape,
1441                                                               {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
1442                        make_host_tensor<element::Type_t::i64>(axis_shape, {-1})}));
1443
1444     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1445     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3}));
1446     auto cval = read_vector<float>(result_tensor);
1447     vector<float> out{1.1f, 1.0f, 1.2f, 2.0f, 2.2f, 2.1f, 0.0f, 0.0f, 0.0f};
1448     ASSERT_EQ(cval, out);
1449 }
1450
1451 TEST(eval, evaluate_dynamic_scatter_elements_update_1d_axis)
1452 {
1453     const Shape data_shape{3, 3};
1454     const Shape indices_shape{2, 3};
1455
1456     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1457     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1458     auto arg3 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1459     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
1460
1461     auto scatter_elements_update =
1462         make_shared<op::v3::ScatterElementsUpdate>(arg1, arg2, arg3, arg4);
1463     auto fun = make_shared<Function>(OutputVector{scatter_elements_update},
1464                                      ParameterVector{arg1, arg2, arg3, arg4});
1465     auto result_tensor = make_shared<HostTensor>();
1466     ASSERT_TRUE(
1467         fun->evaluate({result_tensor},
1468                       {make_host_tensor<element::Type_t::f32>(
1469                            data_shape, {0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f, 0.f}),
1470                        make_host_tensor<element::Type_t::i32>(indices_shape, {1, 0, 2, 0, 2, 1}),
1471                        make_host_tensor<element::Type_t::f32>(indices_shape,
1472                                                               {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
1473                        make_host_tensor<element::Type_t::i64>({1}, {0})}));
1474
1475     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1476     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3}));
1477     auto cval = read_vector<float>(result_tensor);
1478     vector<float> out{2.f, 1.1f, 0.0f, 1.f, 0.0f, 2.2f, 0.f, 2.1f, 1.2f};
1479     ASSERT_EQ(cval, out);
1480 }
1481
1482 // Disabled test for disabled reference implementation
1483 TEST(eval, DISABLED_evaluate_dynamic_scatter_elements_update_3d_i16)
1484 {
1485     const Shape data_shape{3, 3, 3};
1486     const Shape indices_shape{2, 2, 3};
1487
1488     auto arg1 = make_shared<op::Parameter>(element::i16, PartialShape::dynamic());
1489     auto arg2 = make_shared<op::Parameter>(element::i16, PartialShape::dynamic());
1490     auto arg3 = make_shared<op::Parameter>(element::i16, PartialShape::dynamic());
1491     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
1492
1493     auto scatter_elements_update =
1494         make_shared<op::v3::ScatterElementsUpdate>(arg1, arg2, arg3, arg4);
1495     auto fun = make_shared<Function>(OutputVector{scatter_elements_update},
1496                                      ParameterVector{arg1, arg2, arg3, arg4});
1497     auto result_tensor = make_shared<HostTensor>();
1498     ASSERT_TRUE(fun->evaluate({result_tensor},
1499                               {make_host_tensor<element::Type_t::i16>(
1500                                    data_shape, {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1501                                                 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}),
1502                                make_host_tensor<element::Type_t::i16>(
1503                                    indices_shape, {1, 0, 2, 0, 2, 1, 2, 2, 2, 0, 1, 0}),
1504                                make_host_tensor<element::Type_t::i16>(
1505                                    indices_shape, {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12}),
1506                                make_host_tensor<element::Type_t::i64>({}, {1})}));
1507
1508     EXPECT_EQ(result_tensor->get_element_type(), element::i16);
1509     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3, 3}));
1510     auto cval = read_vector<int16_t>(result_tensor);
1511     vector<int16_t> out{4, 2, 0, 1, 0, 6, 0, 5, 3, 10, 0, 12, 0, 11,
1512                         0, 7, 8, 9, 0, 0, 0, 0, 0, 0,  0, 0,  0};
1513     ASSERT_EQ(cval, out);
1514 }
1515
1516 TEST(eval, evaluate_dynamic_scatter_elements_update_one_elem_i32)
1517 {
1518     const Shape data_shape{3, 3, 3};
1519     const Shape indices_shape{1, 1, 1};
1520
1521     auto arg1 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1522     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1523     auto arg3 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1524     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
1525
1526     auto scatter_elements_update =
1527         make_shared<op::v3::ScatterElementsUpdate>(arg1, arg2, arg3, arg4);
1528     auto fun = make_shared<Function>(OutputVector{scatter_elements_update},
1529                                      ParameterVector{arg1, arg2, arg3, arg4});
1530     auto result_tensor = make_shared<HostTensor>();
1531     ASSERT_TRUE(fun->evaluate({result_tensor},
1532                               {make_host_tensor<element::Type_t::i32>(
1533                                    data_shape, {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1534                                                 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}),
1535                                make_host_tensor<element::Type_t::i32>(indices_shape, {1}),
1536                                make_host_tensor<element::Type_t::i32>(indices_shape, {2}),
1537                                make_host_tensor<element::Type_t::i64>({}, {0})}));
1538
1539     EXPECT_EQ(result_tensor->get_element_type(), element::i32);
1540     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3, 3}));
1541     auto cval = read_vector<int32_t>(result_tensor);
1542     vector<int32_t> out{0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0,
1543                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
1544     ASSERT_EQ(cval, out);
1545 }
1546
1547 TEST(eval, topk_v1)
1548 {
1549     Shape shape{2, 3, 2};
1550     Shape rshape{2, 2, 2};
1551
1552     auto A = make_shared<op::Parameter>(element::f32, shape);
1553     const auto k = op::Constant::create(element::i32, Shape{}, {2});
1554     auto B = make_shared<op::v1::TopK>(A, k, 1, "max", "index", element::i32);
1555
1556     auto fun = make_shared<Function>(OutputVector{B->output(0), B->output(1)}, ParameterVector{A});
1557
1558     auto result0 = make_shared<HostTensor>();
1559     auto result1 = make_shared<HostTensor>();
1560     ASSERT_TRUE(fun->evaluate({result0, result1},
1561                               {make_host_tensor<element::Type_t::f32>(
1562                                   Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7})}));
1563     EXPECT_EQ(result0->get_element_type(), element::f32);
1564     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 2, 2}));
1565     EXPECT_EQ(result1->get_element_type(), element::i32);
1566     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 2, 2}));
1567     auto result0_val = read_vector<float>(result0);
1568
1569     auto result1_val = read_vector<int32_t>(result1);
1570
1571     vector<float> expec0{12, 9, 10, 4, 6, 3, 11, 7};
1572     ASSERT_EQ(result0_val, expec0);
1573
1574     vector<int32_t> expec1{0, 1, 1, 2, 0, 1, 2, 2};
1575     ASSERT_EQ(result1_val, expec1);
1576 }
1577
1578 TEST(eval, topk_v1_dyn)
1579 {
1580     Shape shape{2, 3, 2};
1581
1582     auto A = make_shared<op::Parameter>(element::f32, shape);
1583     auto k = make_shared<op::Parameter>(element::u32, Shape{});
1584     auto B = make_shared<op::v1::TopK>(A, k, 1, "max", "index", element::i32);
1585
1586     auto fun =
1587         make_shared<Function>(OutputVector{B->output(0), B->output(1)}, ParameterVector{A, k});
1588
1589     auto result0 = make_shared<HostTensor>();
1590     auto result1 = make_shared<HostTensor>();
1591     ASSERT_TRUE(fun->evaluate({result0, result1},
1592                               {make_host_tensor<element::Type_t::f32>(
1593                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1594                                make_host_tensor<element::Type_t::i32>(Shape{}, {2})}));
1595     EXPECT_EQ(result0->get_element_type(), element::f32);
1596     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 2, 2}));
1597     EXPECT_EQ(result1->get_element_type(), element::i32);
1598     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 2, 2}));
1599     auto result0_val = read_vector<float>(result0);
1600     auto result1_val = read_vector<int32_t>(result1);
1601     vector<float> expec0{12, 9, 10, 4, 6, 3, 11, 7};
1602     ASSERT_EQ(result0_val, expec0);
1603
1604     vector<int32_t> expec1{0, 1, 1, 2, 0, 1, 2, 2};
1605     ASSERT_EQ(result1_val, expec1);
1606 }
1607
1608 TEST(eval, topk_v3_dyn)
1609 {
1610     Shape shape{2, 3, 2};
1611
1612     auto A = make_shared<op::Parameter>(element::f32, shape);
1613     auto k = make_shared<op::Parameter>(element::u32, Shape{});
1614     auto B = make_shared<op::v3::TopK>(A, k, 1, "max", "index", element::i32);
1615
1616     auto fun =
1617         make_shared<Function>(OutputVector{B->output(0), B->output(1)}, ParameterVector{A, k});
1618
1619     auto result0 = make_shared<HostTensor>();
1620     auto result1 = make_shared<HostTensor>();
1621     ASSERT_TRUE(fun->evaluate({result0, result1},
1622                               {make_host_tensor<element::Type_t::f32>(
1623                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1624                                make_host_tensor<element::Type_t::i32>(Shape{}, {2})}));
1625     EXPECT_EQ(result0->get_element_type(), element::f32);
1626     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 2, 2}));
1627     EXPECT_EQ(result1->get_element_type(), element::i32);
1628     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 2, 2}));
1629     auto result0_val = read_vector<float>(result0);
1630     auto result1_val = read_vector<int32_t>(result1);
1631     vector<float> expec0{12, 9, 10, 4, 6, 3, 11, 7};
1632     ASSERT_EQ(result0_val, expec0);
1633
1634     vector<int32_t> expec1{0, 1, 1, 2, 0, 1, 2, 2};
1635     ASSERT_EQ(result1_val, expec1);
1636 }
1637
1638 TEST(eval, topk_v3_dyn_values)
1639 {
1640     Shape shape{2, 3, 2};
1641
1642     auto A = make_shared<op::Parameter>(element::f32, shape);
1643     auto k = make_shared<op::Parameter>(element::u32, Shape{});
1644     auto B = make_shared<op::v3::TopK>(A, k, 1, "max", "value", element::i32);
1645
1646     auto fun =
1647         make_shared<Function>(OutputVector{B->output(0), B->output(1)}, ParameterVector{A, k});
1648
1649     auto result0 = make_shared<HostTensor>();
1650     auto result1 = make_shared<HostTensor>();
1651     ASSERT_TRUE(fun->evaluate({result0, result1},
1652                               {make_host_tensor<element::Type_t::f32>(
1653                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1654                                make_host_tensor<element::Type_t::i32>(Shape{}, {2})}));
1655     EXPECT_EQ(result0->get_element_type(), element::f32);
1656     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 2, 2}));
1657     EXPECT_EQ(result1->get_element_type(), element::i32);
1658     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 2, 2}));
1659     auto result0_val = read_vector<float>(result0);
1660     auto result1_val = read_vector<int32_t>(result1);
1661     vector<float> expec0{12, 9, 10, 4, 11, 7, 6, 3};
1662     ASSERT_EQ(result0_val, expec0);
1663
1664     vector<int32_t> expec1{0, 1, 1, 2, 2, 2, 0, 1};
1665     ASSERT_EQ(result1_val, expec1);
1666 }
1667
1668 TEST(eval, topk_v3_dyn_values_k0)
1669 {
1670     Shape shape{2, 3, 2};
1671
1672     auto A = make_shared<op::Parameter>(element::f32, shape);
1673     auto k = make_shared<op::Parameter>(element::u32, Shape{});
1674     auto B = make_shared<op::v3::TopK>(A, k, 1, "max", "value", element::i32);
1675
1676     auto fun =
1677         make_shared<Function>(OutputVector{B->output(0), B->output(1)}, ParameterVector{A, k});
1678
1679     auto result0 = make_shared<HostTensor>();
1680     auto result1 = make_shared<HostTensor>();
1681     ASSERT_TRUE(fun->evaluate({result0, result1},
1682                               {make_host_tensor<element::Type_t::f32>(
1683                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1684                                make_host_tensor<element::Type_t::i32>(Shape{}, {0})}));
1685     EXPECT_EQ(result0->get_element_type(), element::f32);
1686     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 3, 2}));
1687     EXPECT_EQ(result1->get_element_type(), element::i32);
1688     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 3, 2}));
1689     auto result0_val = read_vector<float>(result0);
1690     auto result1_val = read_vector<int32_t>(result1);
1691     vector<float> expec0{12, 9, 10, 4, 8, 2, 11, 7, 6, 3, 5, 1};
1692     ASSERT_EQ(result0_val, expec0);
1693
1694     vector<int32_t> expec1{0, 1, 1, 2, 2, 0, 2, 2, 0, 1, 1, 0};
1695     ASSERT_EQ(result1_val, expec1);
1696 }
1697
1698 TEST(eval, topk_v0_dyn)
1699 {
1700     Shape shape{2, 3, 2};
1701
1702     auto A = make_shared<op::Parameter>(element::f32, shape);
1703     auto k = make_shared<op::Parameter>(element::i64, Shape{});
1704     auto axis = make_shared<op::Parameter>(element::i64, Shape{});
1705
1706     element::Type result_et{element::i32};
1707     bool compute_max = true;
1708
1709     auto B = make_shared<op::v0::TopK>(
1710         A, k, axis, result_et, compute_max, op::v0::TopK::SortType::SORT_VALUES);
1711
1712     auto fun = make_shared<Function>(OutputVector{B->output(0), B->output(1)},
1713                                      ParameterVector{A, k, axis});
1714
1715     auto result0 = make_shared<HostTensor>();
1716     auto result1 = make_shared<HostTensor>();
1717     ASSERT_TRUE(fun->evaluate({result0, result1},
1718                               {make_host_tensor<element::Type_t::f32>(
1719                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1720                                make_host_tensor<element::Type_t::i64>(Shape{}, {2}),
1721                                make_host_tensor<element::Type_t::i64>(Shape{}, {1})}));
1722     EXPECT_EQ(result0->get_element_type(), element::i32);
1723     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 2, 2}));
1724     EXPECT_EQ(result1->get_element_type(), element::f32);
1725     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 2, 2}));
1726     auto result1_val = read_vector<float>(result1);
1727     auto result0_val = read_vector<int32_t>(result0);
1728
1729     vector<float> expec1{12, 9, 10, 4, 11, 7, 6, 3};
1730     ASSERT_EQ(result1_val, expec1);
1731
1732     vector<int32_t> expec0{0, 1, 1, 2, 2, 2, 0, 1};
1733     ASSERT_EQ(result0_val, expec0);
1734 }
1735
1736 TEST(eval, topk_v0_dyn_k0)
1737 {
1738     Shape shape{2, 3, 2};
1739
1740     auto A = make_shared<op::Parameter>(element::f32, shape);
1741     auto k = make_shared<op::Parameter>(element::i64, Shape{});
1742     auto axis = make_shared<op::Parameter>(element::i64, Shape{});
1743
1744     element::Type result_et{element::i32};
1745     bool compute_max = true;
1746
1747     auto B = make_shared<op::v0::TopK>(
1748         A, k, axis, result_et, compute_max, op::v0::TopK::SortType::SORT_VALUES);
1749
1750     auto fun = make_shared<Function>(OutputVector{B->output(0), B->output(1)},
1751                                      ParameterVector{A, k, axis});
1752
1753     auto result0 = make_shared<HostTensor>();
1754     auto result1 = make_shared<HostTensor>();
1755     ASSERT_TRUE(fun->evaluate({result0, result1},
1756                               {make_host_tensor<element::Type_t::f32>(
1757                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1758                                make_host_tensor<element::Type_t::i64>(Shape{}, {0}),
1759                                make_host_tensor<element::Type_t::i64>(Shape{}, {1})}));
1760     EXPECT_EQ(result0->get_element_type(), element::i32);
1761     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 3, 2}));
1762     EXPECT_EQ(result1->get_element_type(), element::f32);
1763     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 3, 2}));
1764     auto result1_val = read_vector<float>(result1);
1765     auto result0_val = read_vector<int32_t>(result0);
1766
1767     vector<float> expec1{12, 9, 10, 4, 8, 2, 11, 7, 6, 3, 5, 1};
1768     ASSERT_EQ(result1_val, expec1);
1769
1770     vector<int32_t> expec0{0, 1, 1, 2, 2, 0, 2, 2, 0, 1, 1, 0};
1771     ASSERT_EQ(result0_val, expec0);
1772 }
1773
1774 TEST(eval, topk_v3_param_dyn_values_k0)
1775 {
1776     auto A = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1777     auto k = make_shared<op::Parameter>(element::u32, Shape{});
1778     auto B = make_shared<op::v3::TopK>(A, k, 1, "max", "value", element::i32);
1779
1780     auto fun =
1781         make_shared<Function>(OutputVector{B->output(0), B->output(1)}, ParameterVector{A, k});
1782
1783     auto result0 = make_shared<HostTensor>();
1784     auto result1 = make_shared<HostTensor>();
1785     ASSERT_TRUE(fun->evaluate({result0, result1},
1786                               {make_host_tensor<element::Type_t::f32>(
1787                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1788                                make_host_tensor<element::Type_t::i32>(Shape{}, {0})}));
1789     EXPECT_EQ(result0->get_element_type(), element::f32);
1790     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 3, 2}));
1791     EXPECT_EQ(result1->get_element_type(), element::i32);
1792     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 3, 2}));
1793     auto result0_val = read_vector<float>(result0);
1794     auto result1_val = read_vector<int32_t>(result1);
1795     vector<float> expec0{12, 9, 10, 4, 8, 2, 11, 7, 6, 3, 5, 1};
1796     ASSERT_EQ(result0_val, expec0);
1797
1798     vector<int32_t> expec1{0, 1, 1, 2, 2, 0, 2, 2, 0, 1, 1, 0};
1799     ASSERT_EQ(result1_val, expec1);
1800 }
1801
1802 TEST(eval, topk_v3_param_dyn_values_k2)
1803 {
1804     auto A = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1805     auto k = make_shared<op::Parameter>(element::u32, Shape{});
1806     auto B = make_shared<op::v3::TopK>(A, k, 1, "max", "value", element::i32);
1807
1808     auto fun =
1809         make_shared<Function>(OutputVector{B->output(0), B->output(1)}, ParameterVector{A, k});
1810
1811     auto result0 = make_shared<HostTensor>();
1812     auto result1 = make_shared<HostTensor>();
1813     ASSERT_TRUE(fun->evaluate({result0, result1},
1814                               {make_host_tensor<element::Type_t::f32>(
1815                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1816                                make_host_tensor<element::Type_t::i32>(Shape{}, {2})}));
1817     EXPECT_EQ(result0->get_element_type(), element::f32);
1818     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 2, 2}));
1819     EXPECT_EQ(result1->get_element_type(), element::i32);
1820     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 2, 2}));
1821     auto result0_val = read_vector<float>(result0);
1822     auto result1_val = read_vector<int32_t>(result1);
1823     vector<float> expec0{12, 9, 10, 4, 11, 7, 6, 3};
1824     ASSERT_EQ(result0_val, expec0);
1825
1826     vector<int32_t> expec1{0, 1, 1, 2, 2, 2, 0, 1};
1827     ASSERT_EQ(result1_val, expec1);
1828 }
1829
1830 TEST(eval, topk_v0_param_dyn_k2)
1831 {
1832     auto A = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1833     auto k = make_shared<op::Parameter>(element::i64, Shape{});
1834     auto axis = make_shared<op::Parameter>(element::i64, Shape{});
1835
1836     element::Type result_et{element::i32};
1837     bool compute_max = true;
1838
1839     auto B = make_shared<op::v0::TopK>(
1840         A, k, axis, result_et, compute_max, op::v0::TopK::SortType::SORT_VALUES);
1841
1842     auto fun = make_shared<Function>(OutputVector{B->output(0), B->output(1)},
1843                                      ParameterVector{A, k, axis});
1844
1845     auto result0 = make_shared<HostTensor>();
1846     auto result1 = make_shared<HostTensor>();
1847     ASSERT_TRUE(fun->evaluate({result0, result1},
1848                               {make_host_tensor<element::Type_t::f32>(
1849                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1850                                make_host_tensor<element::Type_t::i64>(Shape{}, {2}),
1851                                make_host_tensor<element::Type_t::i64>(Shape{}, {1})}));
1852     EXPECT_EQ(result0->get_element_type(), element::i32);
1853     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 2, 2}));
1854     EXPECT_EQ(result1->get_element_type(), element::f32);
1855     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 2, 2}));
1856     auto result1_val = read_vector<float>(result1);
1857     auto result0_val = read_vector<int32_t>(result0);
1858
1859     vector<float> expec1{12, 9, 10, 4, 11, 7, 6, 3};
1860     ASSERT_EQ(result1_val, expec1);
1861
1862     vector<int32_t> expec0{0, 1, 1, 2, 2, 2, 0, 1};
1863     ASSERT_EQ(result0_val, expec0);
1864 }
1865
1866 TEST(eval, topk_v0_param_dyn_k0)
1867 {
1868     auto A = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1869     auto k = make_shared<op::Parameter>(element::i64, Shape{});
1870     auto axis = make_shared<op::Parameter>(element::i64, Shape{});
1871
1872     element::Type result_et{element::i32};
1873     bool compute_max = true;
1874
1875     auto B = make_shared<op::v0::TopK>(
1876         A, k, axis, result_et, compute_max, op::v0::TopK::SortType::SORT_VALUES);
1877
1878     auto fun = make_shared<Function>(OutputVector{B->output(0), B->output(1)},
1879                                      ParameterVector{A, k, axis});
1880
1881     auto result0 = make_shared<HostTensor>();
1882     auto result1 = make_shared<HostTensor>();
1883     ASSERT_TRUE(fun->evaluate({result0, result1},
1884                               {make_host_tensor<element::Type_t::f32>(
1885                                    Shape{2, 3, 2}, {12, 2, 10, 9, 8, 4, 6, 1, 5, 3, 11, 7}),
1886                                make_host_tensor<element::Type_t::i64>(Shape{}, {0}),
1887                                make_host_tensor<element::Type_t::i64>(Shape{}, {1})}));
1888     EXPECT_EQ(result0->get_element_type(), element::i32);
1889     EXPECT_EQ(result0->get_partial_shape(), (PartialShape{2, 3, 2}));
1890     EXPECT_EQ(result1->get_element_type(), element::f32);
1891     EXPECT_EQ(result1->get_partial_shape(), (PartialShape{2, 3, 2}));
1892     auto result1_val = read_vector<float>(result1);
1893     auto result0_val = read_vector<int32_t>(result0);
1894
1895     vector<float> expec1{12, 9, 10, 4, 8, 2, 11, 7, 6, 3, 5, 1};
1896     ASSERT_EQ(result1_val, expec1);
1897
1898     vector<int32_t> expec0{0, 1, 1, 2, 2, 0, 2, 2, 0, 1, 1, 0};
1899     ASSERT_EQ(result0_val, expec0);
1900 }
1901
1902 TEST(eval, reduce_logical_and__neg_axis)
1903 {
1904     const auto data = make_shared<op::Parameter>(element::boolean, Shape{2, 2, 2});
1905     const auto axes = make_shared<op::Parameter>(element::i64, Shape{});
1906
1907     const auto op = make_shared<op::v1::ReduceLogicalAnd>(data, axes);
1908
1909     auto fun = make_shared<Function>(op, ParameterVector{data, axes});
1910
1911     auto result = make_shared<HostTensor>();
1912
1913     // when ReduceLogicalAnd node evaluator returns false -> the Function object throws
1914     EXPECT_THROW(
1915         fun->evaluate({result},
1916                       {
1917                           make_host_tensor<element::Type_t::boolean>(
1918                               Shape{2, 2, 2}, {true, false, true, false, true, false, true, false}),
1919                           make_host_tensor<element::Type_t::i64>(Shape{}, {-1}),
1920                       }),
1921         ngraph::ngraph_error);
1922 }
1923
1924 TEST(eval, evaluate_static_scatter_update_basic_axes_indices_i32)
1925 {
1926     const Shape data_shape{3, 3};
1927     const Shape indices_shape{1, 2};
1928     const Shape updates_shape{1, 2, 3};
1929
1930     auto arg1 = make_shared<op::Parameter>(element::f32, data_shape);
1931     auto arg2 = make_shared<op::Parameter>(element::i32, indices_shape);
1932     auto arg3 = make_shared<op::Parameter>(element::f32, updates_shape);
1933     auto arg4 = make_shared<op::Parameter>(element::i32, Shape{});
1934     auto scatter_update = make_shared<op::v3::ScatterUpdate>(arg1, arg2, arg3, arg4);
1935     auto fun = make_shared<Function>(OutputVector{scatter_update},
1936                                      ParameterVector{arg1, arg2, arg3, arg4});
1937     auto result_tensor = make_shared<HostTensor>();
1938     ASSERT_TRUE(fun->evaluate({result_tensor},
1939                               {make_host_tensor<element::Type_t::f32>(
1940                                    data_shape, std::vector<float>(shape_size(data_shape))),
1941                                make_host_tensor<element::Type_t::i32>(indices_shape, {1, 2}),
1942                                make_host_tensor<element::Type_t::f32>(
1943                                    updates_shape, {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
1944                                make_host_tensor<element::Type_t::i32>({}, {0})}));
1945     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1946     EXPECT_EQ(result_tensor->get_shape(), (Shape{3, 3}));
1947     auto cval = read_vector<float>(result_tensor);
1948     vector<float> out{0.f, 0.f, 0.f, 1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f};
1949     ASSERT_EQ(cval, out);
1950 }
1951
1952 TEST(eval, evaluate_static_scatter_update_basic_axes_indices_i64)
1953 {
1954     const Shape data_shape{3, 3};
1955     const Shape indices_shape{1, 2};
1956     const Shape updates_shape{1, 2, 3};
1957
1958     auto arg1 = make_shared<op::Parameter>(element::f32, data_shape);
1959     auto arg2 = make_shared<op::Parameter>(element::i64, indices_shape);
1960     auto arg3 = make_shared<op::Parameter>(element::f32, updates_shape);
1961     auto arg4 = make_shared<op::Parameter>(element::i64, Shape{});
1962     auto scatter_update = make_shared<op::v3::ScatterUpdate>(arg1, arg2, arg3, arg4);
1963     auto fun = make_shared<Function>(OutputVector{scatter_update},
1964                                      ParameterVector{arg1, arg2, arg3, arg4});
1965     auto result_tensor = make_shared<HostTensor>();
1966     ASSERT_TRUE(fun->evaluate({result_tensor},
1967                               {make_host_tensor<element::Type_t::f32>(
1968                                    data_shape, std::vector<float>(shape_size(data_shape))),
1969                                make_host_tensor<element::Type_t::i64>(indices_shape, {1, 2}),
1970                                make_host_tensor<element::Type_t::f32>(
1971                                    updates_shape, {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
1972                                make_host_tensor<element::Type_t::i64>({}, {0})}));
1973     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
1974     EXPECT_EQ(result_tensor->get_shape(), (Shape{3, 3}));
1975     auto cval = read_vector<float>(result_tensor);
1976     vector<float> out{0.f, 0.f, 0.f, 1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f};
1977     ASSERT_EQ(cval, out);
1978 }
1979
1980 TEST(eval, evaluate_dynamic_scatter_update_basic)
1981 {
1982     const Shape data_shape{3, 3};
1983     const Shape indices_shape{1, 2};
1984     const Shape updates_shape{1, 2, 3};
1985
1986     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1987     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
1988     auto arg3 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
1989     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
1990
1991     auto scatter_update = make_shared<op::v3::ScatterUpdate>(arg1, arg2, arg3, arg4);
1992     auto fun = make_shared<Function>(OutputVector{scatter_update},
1993                                      ParameterVector{arg1, arg2, arg3, arg4});
1994     auto result_tensor = make_shared<HostTensor>();
1995     ASSERT_TRUE(fun->evaluate({result_tensor},
1996                               {make_host_tensor<element::Type_t::f32>(
1997                                    data_shape, std::vector<float>(shape_size(data_shape))),
1998                                make_host_tensor<element::Type_t::i32>(indices_shape, {1, 2}),
1999                                make_host_tensor<element::Type_t::f32>(
2000                                    updates_shape, {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
2001                                make_host_tensor<element::Type_t::i64>({}, {0})}));
2002
2003     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
2004     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3}));
2005     auto cval = read_vector<float>(result_tensor);
2006     vector<float> out{0.f, 0.f, 0.f, 1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f};
2007     ASSERT_EQ(cval, out);
2008 }
2009
2010 TEST(eval, evaluate_dynamic_scatter_update_negative_axis)
2011 {
2012     const Shape data_shape{3, 3};
2013     const Shape indices_shape{1, 2};
2014     const Shape updates_shape{3, 1, 2};
2015     const Shape axis_shape{};
2016
2017     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
2018     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
2019     auto arg3 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
2020     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
2021
2022     auto scatter_update = make_shared<op::v3::ScatterUpdate>(arg1, arg2, arg3, arg4);
2023     auto fun = make_shared<Function>(OutputVector{scatter_update},
2024                                      ParameterVector{arg1, arg2, arg3, arg4});
2025     auto result_tensor = make_shared<HostTensor>();
2026     ASSERT_TRUE(fun->evaluate({result_tensor},
2027                               {make_host_tensor<element::Type_t::f32>(
2028                                    data_shape, std::vector<float>(shape_size(data_shape))),
2029                                make_host_tensor<element::Type_t::i32>(indices_shape, {1, 2}),
2030                                make_host_tensor<element::Type_t::f32>(
2031                                    updates_shape, {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
2032                                make_host_tensor<element::Type_t::i64>(axis_shape, {-1})}));
2033
2034     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
2035     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3}));
2036     auto cval = read_vector<float>(result_tensor);
2037     vector<float> out{0.f, 1.0f, 1.1f, 0.0f, 1.2f, 2.0f, 0.0f, 2.1f, 2.2f};
2038     ASSERT_EQ(cval, out);
2039 }
2040
2041 TEST(eval, evaluate_dynamic_scatter_update_1d_axis)
2042 {
2043     const Shape data_shape{3, 3};
2044     const Shape indices_shape{1, 2};
2045     const Shape updates_shape{3, 1, 2};
2046
2047     auto arg1 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
2048     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
2049     auto arg3 = make_shared<op::Parameter>(element::f32, PartialShape::dynamic());
2050     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
2051
2052     auto scatter_update = make_shared<op::v3::ScatterUpdate>(arg1, arg2, arg3, arg4);
2053     auto fun = make_shared<Function>(OutputVector{scatter_update},
2054                                      ParameterVector{arg1, arg2, arg3, arg4});
2055     auto result_tensor = make_shared<HostTensor>();
2056     ASSERT_TRUE(fun->evaluate({result_tensor},
2057                               {make_host_tensor<element::Type_t::f32>(
2058                                    data_shape, std::vector<float>(shape_size(data_shape))),
2059                                make_host_tensor<element::Type_t::i32>(indices_shape, {1, 2}),
2060                                make_host_tensor<element::Type_t::f32>(
2061                                    updates_shape, {1.0f, 1.1f, 1.2f, 2.0f, 2.1f, 2.2f}),
2062                                make_host_tensor<element::Type_t::i64>({1}, {1})}));
2063
2064     EXPECT_EQ(result_tensor->get_element_type(), element::f32);
2065     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3}));
2066     auto cval = read_vector<float>(result_tensor);
2067     vector<float> out{0.f, 1.0f, 1.1f, 0.0f, 1.2f, 2.0f, 0.0f, 2.1f, 2.2f};
2068     ASSERT_EQ(cval, out);
2069 }
2070
2071 TEST(eval, evaluate_dynamic_scatter_update_one_elem_i32)
2072 {
2073     const Shape data_shape{3, 3, 2};
2074     const Shape indices_shape{1, 1};
2075     const Shape updates_shape{1, 1, 3, 2};
2076
2077     auto arg1 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
2078     auto arg2 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
2079     auto arg3 = make_shared<op::Parameter>(element::i32, PartialShape::dynamic());
2080     auto arg4 = make_shared<op::Parameter>(element::i64, PartialShape::dynamic());
2081
2082     auto scatter_update = make_shared<op::v3::ScatterUpdate>(arg1, arg2, arg3, arg4);
2083     auto fun = make_shared<Function>(OutputVector{scatter_update},
2084                                      ParameterVector{arg1, arg2, arg3, arg4});
2085     auto result_tensor = make_shared<HostTensor>();
2086     ASSERT_TRUE(
2087         fun->evaluate({result_tensor},
2088                       {make_host_tensor<element::Type_t::i32>(
2089                            data_shape, std::vector<int32_t>(shape_size(data_shape))),
2090                        make_host_tensor<element::Type_t::i32>(indices_shape, {1}),
2091                        make_host_tensor<element::Type_t::i32>(updates_shape, {1, 2, 3, 4, 5, 6}),
2092                        make_host_tensor<element::Type_t::i64>({}, {0})}));
2093
2094     EXPECT_EQ(result_tensor->get_element_type(), element::i32);
2095     EXPECT_EQ(result_tensor->get_partial_shape(), (PartialShape{3, 3, 2}));
2096     auto cval = read_vector<int32_t>(result_tensor);
2097     vector<int32_t> out{0, 0, 0, 0, 0, 0, 1, 2, 3, 4, 5, 6, 0, 0, 0, 0, 0, 0};
2098     ASSERT_EQ(cval, out);
2099 }