diff --git a/aidge_backend_cpu/unit_tests/test_scheduler.py b/aidge_backend_cpu/unit_tests/test_scheduler.py index c37fc54437c02b0bb1c6f09a1c73d5cc538fa4c0..494f34565ffd644971c97e9adfa06709dee9e36d 100644 --- a/aidge_backend_cpu/unit_tests/test_scheduler.py +++ b/aidge_backend_cpu/unit_tests/test_scheduler.py @@ -13,9 +13,10 @@ class test_scheduler(unittest.TestCase): pass def test_relu_forward(self): - values = np.arange(6) - 3 - input_node = aidge_core.Producer(aidge_core.Tensor(values), "Input") + t = aidge_core.Tensor(np.arange(6, dtype=np.int32) - 3) + + input_node = aidge_core.Producer(t) relu = aidge_core.ReLU() input_node.add_child(relu) @@ -34,7 +35,7 @@ class test_scheduler(unittest.TestCase): out_tensor = relu.get_operator().get_output(0) expected_out = [0,0,0,0,1,2] for i in range(len(expected_out)): - self.assertEqual(expected_out[i], out_tensor[i]) + self.assertEqual(expected_out[i], out_tensor[i], f"On idx {i}") def test_sequential_scheduling(self): input_data = np.array([0]).astype(np.float32) @@ -69,7 +70,7 @@ class test_scheduler(unittest.TestCase): aidge_core.Producer(input_tensor, "X"), aidge_core.FC(1, 50, name='0'), aidge_core.parallel([aidge_core.FC(50, 50, name='1'), aidge_core.FC(50, 50, name='3')]), - aidge_core.Add(2, name='2'), + aidge_core.Add(name='2'), ]) EXPECTED_SCHEDULE = [['0', '1', '3', '2'], ['0', '3', '1', '2']] # Both scheduling are valid ! diff --git a/include/aidge/backend/cpu.hpp b/include/aidge/backend/cpu.hpp index b45aa1cb4151d8d6c5268d4a94da97bb25a89a40..760fc71a4b659e1bffe28e2796c7bb400e8ec1a2 100644 --- a/include/aidge/backend/cpu.hpp +++ b/include/aidge/backend/cpu.hpp @@ -15,6 +15,8 @@ #include "aidge/backend/cpu/operator/AbsImpl.hpp" #include "aidge/backend/cpu/operator/AddImpl.hpp" #include "aidge/backend/cpu/operator/AndImpl.hpp" +#include "aidge/backend/cpu/operator/AtanImpl.hpp" + #include "aidge/backend/cpu/operator/ArgMaxImpl.hpp" #include "aidge/backend/cpu/operator/AvgPoolingImpl.hpp" #include "aidge/backend/cpu/operator/MaxPoolingImpl.hpp" diff --git a/include/aidge/backend/cpu/operator/AtanImpl.hpp b/include/aidge/backend/cpu/operator/AtanImpl.hpp new file mode 100644 index 0000000000000000000000000000000000000000..2f1b4bf0ad666ff9856c24fa675b70d6f830b07c --- /dev/null +++ b/include/aidge/backend/cpu/operator/AtanImpl.hpp @@ -0,0 +1,33 @@ +/******************************************************************************** + * Copyright (c) 2023 CEA-List + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License 2.0 which is available at + * http://www.eclipse.org/legal/epl-2.0. + * + * SPDX-License-Identifier: EPL-2.0 + * + ********************************************************************************/ + +#ifndef AIDGE_CPU_OPERATOR_ATAN_H_ +#define AIDGE_CPU_OPERATOR_ATAN_H_ + +#include "aidge/backend/cpu/operator/OperatorImpl.hpp" +#include "aidge/operator/Atan.hpp" +#include "aidge/utils/Registrar.hpp" +#include "aidge/utils/Types.h" +#include "aidge/backend/cpu/data/GetCPUPtr.h" +#include <memory> +#include <vector> + +namespace Aidge { +// Operator implementation entry point for the backend +using AtanImpl_cpu = OperatorImpl_cpu<Atan_Op, + void(const std::size_t, const void*, void*), + void(const std::size_t, const void*, const void*, void*)>; + +// Implementation entry point registration to Operator +REGISTRAR(Atan_Op, "cpu", Aidge::AtanImpl_cpu::create); +} // namespace Aidge + +#endif /* AIDGE_CPU_OPERATOR_ATAN_H_ */ diff --git a/include/aidge/backend/cpu/operator/AtanImpl_kernels.hpp b/include/aidge/backend/cpu/operator/AtanImpl_kernels.hpp new file mode 100644 index 0000000000000000000000000000000000000000..2a786339503354514416705b61cfedfcc0b7c321 --- /dev/null +++ b/include/aidge/backend/cpu/operator/AtanImpl_kernels.hpp @@ -0,0 +1,60 @@ +/******************************************************************************** + * Copyright (c) 2023 CEA-List + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License 2.0 which is available at + * http://www.eclipse.org/legal/epl-2.0. + * + * SPDX-License-Identifier: EPL-2.0 + * + ********************************************************************************/ + +#ifndef AIDGE_CPU_OPERATOR_ATANIMPL_KERNELS_H_ +#define AIDGE_CPU_OPERATOR_ATANIMPL_KERNELS_H_ + +#include "aidge/utils/Registrar.hpp" + +#include "aidge/backend/cpu/operator/AtanImpl.hpp" +#include <cmath> // For atan() + + +namespace Aidge { +template <class I, class O> +void AtanImpl_cpu_forward_kernel(std::size_t inputLenght, + const void* input_, + void* output_) { + const I* input = static_cast<const I*>(input_); + O* output = static_cast<O*>(output_); + + for (size_t i = 0; i < inputLenght; ++i) { + output[i] = static_cast<O>(atan(input[i])); + } + +} + +template <class O, class GI, class GO> +void AtanImpl_cpu_backward_kernel(const std::size_t inputLenght, + const void* output_, const void* grad_output_, + void* grad_input_) { + const O* output = static_cast<const O*>(output_); + const GO* grad_output = static_cast<const GO*>(grad_output_); + GI* grad_input = static_cast<GI*>(grad_input_); + + // Apply the derivative of atan for each element in the input array + for (size_t i = 0; i < inputLenght; ++i) { + // dx = dy * (1 / (1 + x^2)) + grad_input[i] = grad_output[i] * static_cast<O>(1.0 / (1.0 + output[i] * output[i])); + } +} + + +// Kernels registration to implementation entry point +REGISTRAR(AtanImpl_cpu, + {DataType::Float32}, + {ProdConso::inPlaceModel, Aidge::AtanImpl_cpu_forward_kernel<float, float>, Aidge::AtanImpl_cpu_backward_kernel<float, float, float>}); +REGISTRAR(AtanImpl_cpu, + {DataType::Float64}, + {ProdConso::inPlaceModel, Aidge::AtanImpl_cpu_forward_kernel<double, double>, Aidge::AtanImpl_cpu_backward_kernel<double, double, double>}); +} // namespace Aidge + +#endif /* AIDGE_CPU_OPERATOR_ATANIMPL_KERNELS_H_ */ diff --git a/include/aidge/backend/cpu/operator/ConvDepthWiseImpl_kernels.hpp b/include/aidge/backend/cpu/operator/ConvDepthWiseImpl_kernels.hpp index 59a471aee82f7c706be390d80b5db569bd3c6f1e..c39cf9cccb41905653c508b985cf27253e20f686 100644 --- a/include/aidge/backend/cpu/operator/ConvDepthWiseImpl_kernels.hpp +++ b/include/aidge/backend/cpu/operator/ConvDepthWiseImpl_kernels.hpp @@ -137,6 +137,7 @@ void ConvDepthWiseImpl2D_cpu_forward_kernel(const std::array<DimSize_t, 2>& stri const std::size_t oxSize = static_cast<std::size_t>(std::floor(static_cast<float>(inputDims[2] - dilated_kernel_x + strideDims[0]) / static_cast<float>(strideDims[0]))); + // output W size const DimSize_t dilated_kernel_y = dilationDims[1]*(kernelDims[1] - 1) + 1; const std::size_t oySize = diff --git a/include/aidge/backend/cpu/operator/GridSampleImpl_kernels.hpp b/include/aidge/backend/cpu/operator/GridSampleImpl_kernels.hpp index ea62fd010db8c155a3ff86ff8396797da5ebb6be..fa390e4e9585225ab15b39651198cb3aaae77edb 100644 --- a/include/aidge/backend/cpu/operator/GridSampleImpl_kernels.hpp +++ b/include/aidge/backend/cpu/operator/GridSampleImpl_kernels.hpp @@ -96,11 +96,11 @@ void GridSampleImpl1D_cpu_forward_kernel(const GridSample_Op& op, const std::shared_ptr<Tensor>& in1, const std::shared_ptr<Tensor>& out) { - const I* const input = static_cast<const I * const>(in0->getImpl()->rawPtr()); + const I* const input = static_cast<const I *>(in0->getImpl()->rawPtr()); const I* input_ptr = input; - float* const grid = static_cast<float* const>(in1->getImpl()->rawPtr()); + float* const grid = static_cast<float*>(in1->getImpl()->rawPtr()); float* grid_ptr = grid; - O* const output = static_cast<O* const>(out->getImpl()->rawPtr()); + O* const output = static_cast<O*>(out->getImpl()->rawPtr()); O* output_ptr = output; const std::size_t N = in0->dim(0); @@ -243,9 +243,9 @@ void GridSampleImpl2D_cpu_forward_kernel(const GridSample_Op& op, { const I* input = static_cast<const I *>(in0->getImpl()->rawPtr()); const I* input_ptr = input; - float* const grid = static_cast<float* const>(in0->getImpl()->rawPtr()); + float* const grid = static_cast<float*>(in0->getImpl()->rawPtr()); float* grid_ptr = grid; - O* const output = static_cast<O* const>(out->getImpl()->rawPtr()); + O* const output = static_cast<O*>(out->getImpl()->rawPtr()); const std::size_t N = in0->dim(0); const std::size_t C = in0->dim(1); diff --git a/include/aidge/backend/cpu/operator/OperatorImpl.hpp b/include/aidge/backend/cpu/operator/OperatorImpl.hpp index abf94ab9069a07e8f87819cb29c027b1adbfd9c6..45f099e8140395181d8be1600c61024efaa9c6a7 100644 --- a/include/aidge/backend/cpu/operator/OperatorImpl.hpp +++ b/include/aidge/backend/cpu/operator/OperatorImpl.hpp @@ -38,8 +38,10 @@ public: return impl.prodConso(mOp); } - virtual std::set<ImplSpec> getAvailableImplSpecs() const override { - return Registrar<OperatorImpl_cpu>::getKeys(); + virtual std::vector<ImplSpec> getAvailableImplSpecs() const override { + // return Registrar<OperatorImpl_cpu>::getKeys(); // Note: cannot return set due to python binding + std::set<ImplSpec> implSpecsSet = Registrar<OperatorImpl_cpu>::getKeys(); + return std::vector<ImplSpec>(implSpecsSet.begin(), implSpecsSet.end()); } void forward() override; diff --git a/src/operator/AtanImpl.cpp b/src/operator/AtanImpl.cpp new file mode 100644 index 0000000000000000000000000000000000000000..af3393e7eb13fad4b414172edc7d1ab32ffcc573 --- /dev/null +++ b/src/operator/AtanImpl.cpp @@ -0,0 +1,54 @@ +/******************************************************************************** + * Copyright (c) 2023 CEA-List + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License 2.0 which is available at + * http://www.eclipse.org/legal/epl-2.0. + * + * SPDX-License-Identifier: EPL-2.0 + * + ********************************************************************************/ + +#include <cassert> +#include <chrono> // std::chrono::milliseconds +#include <numeric> // std::accumulate +#include <thread> // std::this_thread::sleep_for +#include <vector> + +#include "aidge/operator/Atan.hpp" +#include "aidge/utils/Types.h" +#include "aidge/backend/cpu/data/GetCPUPtr.h" + +#include "aidge/backend/cpu/operator/AtanImpl.hpp" +#include "aidge/backend/cpu/operator/AtanImpl_kernels.hpp" + +template <> +void Aidge::AtanImpl_cpu::forward() { + const Atan_Op& op_ = dynamic_cast<const Atan_Op&>(mOp); + std::shared_ptr<Tensor> in0 = op_.getInput(0); + std::shared_ptr<Tensor> out0 = op_.getOutput(0); + AIDGE_ASSERT(in0, "missing input #0"); + + // Find the correct kernel type + const auto impl = Registrar<AtanImpl_cpu>::create(getBestMatch(getRequiredSpec())); + + // Call kernel + impl.forward(in0->size(), + getCPUPtr(mOp.getRawInput(0)), + getCPUPtr(mOp.getRawOutput(0))); +} + +template <> +void Aidge::AtanImpl_cpu::backward() { + const Atan_Op& op_ = dynamic_cast<const Atan_Op&>(mOp); + std::shared_ptr<Tensor> out0 = op_.getOutput(0); + std::shared_ptr<Tensor> gra_int0 = op_.getInput(0)->grad(); + std::shared_ptr<Tensor> gra_out0 = op_.getOutput(0)->grad(); + AIDGE_ASSERT(out0, "missing output #0 for current {} operator", op_.type()); + + // Find the correct kernel type + const auto impl = Registrar<AtanImpl_cpu>::create(getBestMatch(getRequiredSpec())); + + // Call kernel + impl.backward(gra_int0->size(), getCPUPtr(out0), getCPUPtr(gra_out0), getCPUPtr(gra_int0)); +} diff --git a/unit_tests/data/Test_TensorImpl.cpp b/unit_tests/data/Test_TensorImpl.cpp index 5f870acfb44366632474b7290228658d7a4701dd..4bfa10ab4e3d3f522015dbcb3654e105fbb14525 100644 --- a/unit_tests/data/Test_TensorImpl.cpp +++ b/unit_tests/data/Test_TensorImpl.cpp @@ -35,7 +35,7 @@ TEST_CASE("Test addition of Tensors","[TensorImpl][Add]") { std::uniform_int_distribution<int> boolDist(0,1); // Create MatMul Operator - std::shared_ptr<Node> mySub = Add(2); + std::shared_ptr<Node> mySub = Add(); auto op = std::static_pointer_cast<OperatorTensor>(mySub-> getOperator()); op->setDataType(DataType::Float32); op->setBackend("cpu"); diff --git a/unit_tests/operator/Test_AddImpl.cpp b/unit_tests/operator/Test_AddImpl.cpp index 95a0e96fe6cf8c19beeef2bdbae3c07873996dcf..bca4025705cb1c851dcf3e9accbf016c4535120a 100644 --- a/unit_tests/operator/Test_AddImpl.cpp +++ b/unit_tests/operator/Test_AddImpl.cpp @@ -39,17 +39,6 @@ TEST_CASE("[cpu/operator] Add(forward)", "[Add][CPU]") { } // }); // - SECTION("One input") { - std::shared_ptr<Node> myAdd = Add(1); - auto op = std::static_pointer_cast<OperatorTensor>(myAdd -> getOperator()); - op->associateInput(0, input1); - op->setBackend("cpu"); - op->setDataType(DataType::Int32); - myAdd->forward(); - - REQUIRE(*(op->getOutput(0)) == *input1); - } - SECTION("Two inputs") { std::shared_ptr<Tensor> expectedOutput = std::make_shared<Tensor>(Array4D<int,3,3,3,2> { { @@ -71,7 +60,7 @@ TEST_CASE("[cpu/operator] Add(forward)", "[Add][CPU]") { } }); - std::shared_ptr<Node> myAdd = Add(2); + std::shared_ptr<Node> myAdd = Add(); auto op = std::static_pointer_cast<OperatorTensor>(myAdd -> getOperator()); op->associateInput(0, input1); op->associateInput(1, input1); @@ -82,39 +71,6 @@ TEST_CASE("[cpu/operator] Add(forward)", "[Add][CPU]") { REQUIRE(*(op->getOutput(0)) == *expectedOutput); } - SECTION("Three inputs") { - std::shared_ptr<Tensor> expectedOutput = std::make_shared<Tensor>(Array4D<int,3,3,3,2> { - { - { - {{ 60, 141},{ 63, 144},{ 66, 147}}, - {{ 69, 150},{ 72, 153},{ 75, 156}}, - {{ 78, 159},{ 81, 162},{ 84, 165}} - }, - { - {{ 87, 168},{ 90, 171},{ 93, 174}}, - {{ 96, 177},{ 99, 180},{102, 183}}, - {{105, 186},{108, 189},{111, 192}} - }, - { - {{114, 195},{117, 198},{120, 201}}, - {{123, 204},{126, 207},{129, 210}}, - {{132, 213},{135, 216},{138, 219}} - } - } - }); - - std::shared_ptr<Node> myAdd = Add(3); - auto op = std::static_pointer_cast<OperatorTensor>(myAdd -> getOperator()); - op->associateInput(0, input1); - op->associateInput(1, input1); - op->associateInput(2, input1); - op->setDataType(DataType::Int32); - op->setBackend("cpu"); - myAdd->forward(); - - REQUIRE(*op->getOutput(0) == *expectedOutput); - } - SECTION("Broadcasting") { std::shared_ptr<Tensor> input_0 = std::make_shared<Tensor>(Array4D<int,3,1,3,2> { { // @@ -139,7 +95,7 @@ TEST_CASE("[cpu/operator] Add(forward)", "[Add][CPU]") { } // }); // - std::shared_ptr<Tensor> input_2 = std::make_shared<Tensor>(Array1D<int,2> {{100,200}}); + std::shared_ptr<Tensor> input_2 = std::make_shared<Tensor>(Array1D<int,2> {{100,200}}); std::shared_ptr<Tensor> expectedOutput = std::make_shared<Tensor>(Array4D<int,3,3,3,2> { { // { // @@ -160,16 +116,23 @@ TEST_CASE("[cpu/operator] Add(forward)", "[Add][CPU]") { } // }); // - std::shared_ptr<Node> myAdd = Add(3); - auto op = std::static_pointer_cast<OperatorTensor>(myAdd -> getOperator()); - op->associateInput(0, input_0); - op->associateInput(1, input_1); - op->associateInput(2, input_2); - op->setDataType(DataType::Int32); - op->setBackend("cpu"); - myAdd->forward(); - op->getOutput(0)->print(); + std::shared_ptr<Node> myAdd_0 = Add(); + std::shared_ptr<Node> myAdd_1 = Add(); + auto op_0 = std::static_pointer_cast<OperatorTensor>(myAdd_0 -> getOperator()); + auto op_1 = std::static_pointer_cast<OperatorTensor>(myAdd_1 -> getOperator()); + op_0->associateInput(0, input_0); + op_0->associateInput(1, input_1); + + op_1->associateInput(0, input_2); + op_1->associateInput(1, op_0->getOutput(0)); + op_0->setDataType(DataType::Int32); + op_1->setDataType(DataType::Int32); + op_0->setBackend("cpu"); + op_1->setBackend("cpu"); + myAdd_0->forward(); + myAdd_1->forward(); + op_1->getOutput(0)->print(); expectedOutput->print(); - REQUIRE(*op->getOutput(0) == *expectedOutput); + REQUIRE(*op_1->getOutput(0) == *expectedOutput); } } \ No newline at end of file diff --git a/unit_tests/operator/Test_Atan.cpp b/unit_tests/operator/Test_Atan.cpp new file mode 100644 index 0000000000000000000000000000000000000000..9548e35d81b0423125424a4198d82558c4e57df4 --- /dev/null +++ b/unit_tests/operator/Test_Atan.cpp @@ -0,0 +1,77 @@ +/******************************************************************************** + * Copyright (c) 2023 CEA-List + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License 2.0 which is available at + * http://www.eclipse.org/legal/epl-2.0. + * + * SPDX-License-Identifier: EPL-2.0 + * + ********************************************************************************/ + +#include <catch2/catch_test_macros.hpp> + +#include "aidge/data/Tensor.hpp" +#include "aidge/operator/Atan.hpp" + +#include "aidge/backend/cpu.hpp" + +#include <memory> + +using namespace Aidge; + +TEST_CASE("[cpu/operator] Atan(forward)") { + SECTION("1D Tensor") { + std::shared_ptr<Tensor> input0 = + std::make_shared<Tensor>(Array1D<float, 10>{ + {0.41384590, 0.43120754, 0.93762982, 0.31049860, 0.77547199, + 0.09514862, 0.16145366, 0.42776686, 0.43487436, 0.41170865}}); + std::shared_ptr<Tensor> expectedOutput = + std::make_shared<Tensor>(Array1D<float, 10>{ + {0.39238522, 0.40711672, 0.75322037, 0.30106049, 0.65960488, + 0.09486303, 0.16007232, 0.40421187, 0.4102045, 0.39055911}}); + + std::shared_ptr<Node> myAtan = Atan(); + auto op = std::static_pointer_cast<OperatorTensor>(myAtan->getOperator()); + op->associateInput(0, input0); + op->setDataType(DataType::Float32); + op->setBackend("cpu"); + myAtan->forward(); + + float* resPtr = static_cast<float*>(op->getOutput(0)->getImpl()->rawPtr()); + float* expectedPtr = + static_cast<float*>(expectedOutput->getImpl()->rawPtr()); + for (std::size_t i = 0; i < expectedOutput->size(); ++i) { + REQUIRE(std::abs(resPtr[i] - expectedPtr[i]) < 0.00001); + } + } + + SECTION("3D Tensor") { + std::shared_ptr<Tensor> input0 = std::make_shared<Tensor>( + Array3D<float, 2, 2, 3>{{{ + {0.97037154, 0.86208081, 0.77767169}, + {0.38160080, 0.11422747, 0.77284443}, + }, + {{0.51592529, 0.72543722, 0.54641193}, + {0.93866944, 0.97767913, 0.34172094}}}}); + std::shared_ptr<Tensor> expectedOutput = std::make_shared<Tensor>( + Array3D<float, 2, 2, 3>{{{{0.77036231, 0.71146592, 0.66097706}, + {0.36454508, 0.11373451, 0.65796196}}, + {{0.47630652, 0.62759472, 0.50008428}, + {0.75377332, 0.77411225, 0.32928031}}}}); + + std::shared_ptr<Node> myAtan = Atan(); + auto op = std::static_pointer_cast<OperatorTensor>(myAtan->getOperator()); + op->associateInput(0, input0); + op->setDataType(DataType::Float32); + op->setBackend("cpu"); + myAtan->forward(); + + float* resPtr = static_cast<float*>(op->getOutput(0)->getImpl()->rawPtr()); + float* expectedPtr = + static_cast<float*>(expectedOutput->getImpl()->rawPtr()); + for (std::size_t i = 0; i < expectedOutput->size(); ++i) { + REQUIRE(std::abs(resPtr[i] - expectedPtr[i]) < 0.00001); + } + } +} diff --git a/unit_tests/recipies/Test_ConstantFolding.cpp b/unit_tests/recipies/Test_ConstantFolding.cpp index c4866b1258702b93a1bce80501d9acd094a65741..cd035fd5336d3cb66fc70b1c0a4e5c82c9bef0d8 100644 --- a/unit_tests/recipies/Test_ConstantFolding.cpp +++ b/unit_tests/recipies/Test_ConstantFolding.cpp @@ -22,12 +22,12 @@ using namespace Aidge; -TEST_CASE("[ConstantFolding] test") { +TEST_CASE("[ConstantFolding] forward", "[ConstantFolding][forward][CPU]") { // generate the original GraphView auto matmul0 = MatMul("matmul0"); - auto add0 = Add(2, "add0"); + auto add0 = Add("add0"); auto matmul1 = MatMul("matmul1"); - auto add1 = Add(2, "add1"); + auto add1 = Add("add1"); auto b0 = Producer(std::make_shared<Tensor>(Array1D<float,5>{{1, 2, 3, 4, 5}}), "B0", true); auto w0 = Producer(std::make_shared<Tensor>(Array2D<float,5,5>{{{1, 2, 3, 4, 5}, {6, 7, 8, 9, 0}, {1, 2, 3, 4, 5}, {6, 7, 8, 9, 0}, {1, 2, 3, 4, 5}}}), "W0", true); diff --git a/unit_tests/scheduler/Test_Scheduler.cpp b/unit_tests/scheduler/Test_Scheduler.cpp index 16112628053a35ef71d5819a53aacc85425da88d..78a10c308a60f026b83ea64cfbd25a848099eb90 100644 --- a/unit_tests/scheduler/Test_Scheduler.cpp +++ b/unit_tests/scheduler/Test_Scheduler.cpp @@ -147,10 +147,13 @@ TEST_CASE("[cpu/scheduler] SequentialScheduler(forward)") { std::shared_ptr<GraphView> g = Sequential({Conv(1, 3, {3, 3}, "inputConv"), Parallel({ - Conv(3, 3, {1, 1}, "conv1.1"), - Conv(3, 3, {1, 1}, "conv1.2"), + Sequential({ + Parallel({ + Conv(3, 3, {1, 1}, "conv1.1"), + Conv(3, 3, {1, 1}, "conv1.2")}), + Add("add1")}), Conv(3, 3, {1, 1}, "conv1.3")}), - Add(3, "add1"), + Add("add2"), Conv(3, 2, {1, 1}, "conv2"), FC(18, 5, false, "out")}); @@ -216,9 +219,9 @@ TEST_CASE("[cpu/scheduler] SequentialScheduler(forward)") { std::shared_ptr<Tensor> biasTensor = std::make_shared<Tensor>( Array2D<int, 2, 3>{{{2, 0, 0}, {1, 0, 0}}}); - auto add1 = Add(2, "add1"); + auto add1 = Add("add1"); auto mem = Memorize(3, "mem1"); - auto add2 = Add(2, "add2"); + auto add2 = Add("add2"); auto bias = Producer(biasTensor, "bias"); auto init = Producer(initTensor, "init"); auto input = Producer(in, "input"); @@ -260,9 +263,9 @@ TEST_CASE("[cpu/scheduler] SequentialScheduler(forward)") { std::shared_ptr<Tensor> biasTensor = std::make_shared<Tensor>( Array2D<int, 2, 3>{{{2, 0, 0}, {1, 0, 0}}}); - auto add1 = Add(2, "add1"); + auto add1 = Add("add1"); auto mem = Memorize(3, "mem1"); - auto add2 = Add(2, "add2"); + auto add2 = Add("add2"); auto bias = Producer(biasTensor, "bias"); auto init = Producer(initTensor, "init"); auto input = Producer(in, "input");