From 872b798baabdfed1c0db339df0fbf6f1335c68f0 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Tue, 15 Oct 2024 16:50:13 +0300 Subject: [PATCH 01/14] init build graph --- app/CMakeLists.txt | 2 +- app/Graph/CMakeLists.txt | 43 ++++++++++++ app/Graph/build.cpp | 3 + app/Graph/build.hpp | 3 + app/Graph/graph_build.cpp | 137 ++++++++++++++++++++++++++++++++++++++ 5 files changed, 187 insertions(+), 1 deletion(-) create mode 100644 app/Graph/CMakeLists.txt create mode 100644 app/Graph/build.cpp create mode 100644 app/Graph/build.hpp create mode 100644 app/Graph/graph_build.cpp diff --git a/app/CMakeLists.txt b/app/CMakeLists.txt index f9590f8b..3d88e031 100644 --- a/app/CMakeLists.txt +++ b/app/CMakeLists.txt @@ -1,4 +1,4 @@ add_subdirectory(ReaderImage) - add_subdirectory(Accuracy) add_subdirectory(AlexNet) +add_subdirectory(Graph) diff --git a/app/Graph/CMakeLists.txt b/app/Graph/CMakeLists.txt new file mode 100644 index 00000000..93b8c542 --- /dev/null +++ b/app/Graph/CMakeLists.txt @@ -0,0 +1,43 @@ +file(MAKE_DIRECTORY "${CMAKE_SOURCE_DIR}/3rdparty/opencv/build") + +execute_process( + COMMAND ${CMAKE_COMMAND} -S "${CMAKE_SOURCE_DIR}/3rdparty/opencv" -B "${CMAKE_SOURCE_DIR}/3rdparty/opencv/build" -DCMAKE_C_COMPILER_LAUNCHER=${CMAKE_C_COMPILER_LAUNCHER} -DCMAKE_CXX_COMPILER_LAUNCHER=${CMAKE_CXX_COMPILER_LAUNCHER} -DCMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE} -DBUILD_PERF_TESTS=OFF -DBUILD_TESTS=OFF -DBUILD_opencv_apps=OFF + WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}/3rdparty/opencv/build" +) +execute_process( + COMMAND ${CMAKE_COMMAND} --build "${CMAKE_SOURCE_DIR}/3rdparty/opencv/build" --config "${CMAKE_BUILD_TYPE}" + WORKING_DIRECTORY "${CMAKE_SOURCE_DIR}/3rdparty/opencv/build" +) + +set(INCLUDE_HEADERS "${CMAKE_CURRENT_SOURCE_DIR}/build.hpp") +set(SRC_FILES "${CMAKE_CURRENT_SOURCE_DIR}/build.cpp") +add_library(BuildGraph STATIC ${INCLUDE_HEADERS} ${SRC_FILES}) + +set_target_properties(ReadLib PROPERTIES LINKER_LANGUAGE CXX) + +find_package( OpenCV REQUIRED PATHS "${CMAKE_SOURCE_DIR}/3rdparty/opencv/build" ) +include_directories( ${OpenCV_INCLUDE_DIRS} ) +target_link_libraries( BuildGraph ${OpenCV_LIBS} ) +target_link_libraries( BuildGraph TBB::tbb) +target_link_libraries( BuildGraph layers_lib) +target_link_libraries( BuildGraph gtest_main) + +add_executable(Graph_Build graph_build.cpp) +target_link_libraries(Graph_Build BuildGraph) + +if (WIN32) +add_custom_command(TARGET Graph_Build POST_BUILD + COMMAND ${CMAKE_COMMAND} -E copy_directory + "${CMAKE_SOURCE_DIR}/3rdparty/opencv/build/bin/${CMAKE_BUILD_TYPE}" + "${CMAKE_BINARY_DIR}/app/ReaderImage/${CMAKE_BUILD_TYPE}/") +endif() + +file(DOWNLOAD + "https://raw.githubusercontent.com/opencv/opencv/4.x/samples/data/lena.jpg" + "${CMAKE_CURRENT_BINARY_DIR}/image.jpg" + SHOW_PROGRESS + STATUS status_code + LOG log_file +) +add_definitions(-DIMAGE1_PATH="${CMAKE_CURRENT_BINARY_DIR}/image.jpg") +add_definitions(-DMODEL_PATH="${CMAKE_SOURCE_DIR}/docs/model_data_alexnet_1.json") diff --git a/app/Graph/build.cpp b/app/Graph/build.cpp new file mode 100644 index 00000000..f7b3fddd --- /dev/null +++ b/app/Graph/build.cpp @@ -0,0 +1,3 @@ +#include "build.hpp" + +#include \ No newline at end of file diff --git a/app/Graph/build.hpp b/app/Graph/build.hpp new file mode 100644 index 00000000..d552a851 --- /dev/null +++ b/app/Graph/build.hpp @@ -0,0 +1,3 @@ +#pragma once +#include +#include diff --git a/app/Graph/graph_build.cpp b/app/Graph/graph_build.cpp new file mode 100644 index 00000000..cf581849 --- /dev/null +++ b/app/Graph/graph_build.cpp @@ -0,0 +1,137 @@ +#include "Weights_Reader/reader_weights.hpp" +#include "graph/graph.hpp" +#include "layers/ConvLayer.hpp" +#include "layers/EWLayer.hpp" +#include "layers/FCLayer.hpp" +#include "layers/InputLayer.hpp" +#include "layers/OutputLayer.hpp" +#include "layers/PoolingLayer.hpp" +#include +#include +#include "build.hpp" + +using namespace itlab_2023; + +void build_graph(Tensor input) { + + std::string json_file = MODEL_PATH; + json model_data = read_json(json_file); + + + int number_of_layers; + ConvolutionalLayer conv1; + ConvolutionalLayer conv2; + ConvolutionalLayer conv3; + ConvolutionalLayer conv4; + ConvolutionalLayer conv5; + FCLayer fc1; + FCLayer fc2; + FCLayer fc1; + FCLayer fc4; + + + for (auto& layer : model_data.items()) { + number_of_layers++; + std::string layer_name = layer.key(); + Tensor tensor = create_tensor_from_json(layer.value(), Type::kFloat); + if (layer_name == "layer_conv_1") { + ConvolutionalLayer conv1(1, 0, 0, tensor); + } + if (layer_name == "layer_conv_2") { + ConvolutionalLayer conv2(1, 0, 0, tensor); + } + if (layer_name == "layer_conv_3") { + ConvolutionalLayer conv3(1, 0, 0, tensor); + } + if (layer_name == "layer_conv_4") { + ConvolutionalLayer conv4(1, 0, 0, tensor); + } + if (layer_name == "layer_conv_5") { + ConvolutionalLayer conv5(1, 0, 0, tensor); + } + if (layer_name == "dense") { + FCLayer fc1 (tensor, tensor.get_bias()); + } + if (layer_name == "dense_1") { + FCLayer fc2(tensor, tensor.get_bias()); + } + if (layer_name == "dense_2") { + FCLayer fc3(tensor, tensor.get_bias()); + } + if (layer_name == "layer_conv_4") { + FCLayer fc4(tensor, tensor.get_bias()); + } + } + + + Shape sh1({1, 5, 5, 3}); + std::vector vec; + vec.reserve(75); + for (int i = 0; i < 75; ++i) { + vec.push_back(3); + } + Graph graph(number_of_layers); + Tensor output = make_tensor(vec, sh1); + InputLayer a1(kNhwc, kNchw, 1, 2); + Shape poolshape = {2, 2}; + //EWLayer a3("linear", 2.0F, 3.0F); + PoolingLayer pool1(poolshape, "average"); + PoolingLayer pool2(poolshape, "average"); + PoolingLayer pool3(poolshape, "average"); + PoolingLayer pool4(poolshape, "average"); + OutputLayer output; + + + graph.setInput(a1, input); + graph.makeConnection(a1, conv1); + graph.makeConnection(conv1, pool1); + graph.makeConnection(pool1, conv2); + graph.makeConnection(conv2, pool2); + graph.makeConnection(pool2, conv3); + graph.makeConnection(conv3, conv4); + graph.makeConnection(conv4, conv5); + graph.makeConnection(conv5, pool3); + graph.makeConnection(pool3, /* flatten1*/); + graph.makeConnection(/* flatten1*/, fc1); + graph.makeConnection(fc1, fc2); + graph.makeConnection(fc2, /*dropout*/); + graph.setOutput(/*dropout*/, output); + graph.inference(); + + std::vector tmp = *output.as(); + std::vector tmp_output = softmax(*output.as()); + for (float i : tmp) { + std::cout << i << " "; + } +} + +int main() { + std::string image_path = IMAGE1_PATH; + cv::Mat image = cv::imread(image_path); + if (image.empty()) { + throw std::runtime_error("Failed to load image"); + } + cv::Mat resized_image; + cv::resize(image, resized_image, cv::Size(227, 227)); + std::vector channels; + cv::split(resized_image, channels); + int count_pic = 1; + std::vector res(count_pic * 227 * 227 * 3); + int c = 0; + for (int i = 0; i < 227; ++i) { + for (int j = 0; j < 227; ++j) { + res[c] = channels[2].at(i, j); + c++; + res[c] = channels[1].at(i, j); + c++; + res[c] = channels[0].at(i, j); + c++; + } + } + Shape sh({static_cast(count_pic), 227, 227, 3}); + Tensor t = make_tensor(res, sh); + Tensor input = t; //////////////////// + + + build_graph(t); +} \ No newline at end of file From 808ab03c4dbbcf6770a394ba3c747d6ee470605b Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Tue, 22 Oct 2024 21:22:03 +0300 Subject: [PATCH 02/14] fix parcer --- app/AlexNet/parser.py | 40 ++++---- app/AlexNet/reader_weights_sample.cpp | 14 ++- app/Graph/graph_build.cpp | 133 ++++++++++++-------------- include/layers/Tensor.hpp | 1 + src/Weights_Reader/reader_weights.cpp | 3 - 5 files changed, 94 insertions(+), 97 deletions(-) diff --git a/app/AlexNet/parser.py b/app/AlexNet/parser.py index eb0a953c..84d734a5 100644 --- a/app/AlexNet/parser.py +++ b/app/AlexNet/parser.py @@ -4,28 +4,34 @@ import numpy as np import os +# Пути к модели и JSON файлу BASE_DIR = os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))) MODEL_PATH = os.path.join(BASE_DIR, 'docs', 'AlexNet-model.h5') -MODEL_DATA_PATH = os.path.join(BASE_DIR, 'docs', 'model_data_alexnet_1.json') - +MODEL_DATA_PATH = os.path.join(BASE_DIR, 'docs', 'model_data_alexnet_with_order.json') # Загрузка модели model = load_model(MODEL_PATH) -# Получение весов модели -weights = model.get_weights() - - -# Сохранение имен слоев и весов модели -layer_weights = {} -for layer in model.layers: +# Получение весов модели и информации о порядке слоев +layer_info = [] +for index, layer in enumerate(model.layers): layer_name = layer.name + layer_type = type(layer).__name__ # Тип слоя (например, Conv2D, Dense и т.д.) + # Преобразование весов в списки для совместимости с JSON - layer_weights[layer_name] = [w.tolist() for w in layer.get_weights()] + layer_weights = [w.tolist() for w in layer.get_weights()] + + # Сохранение информации о слое: его тип, имя и веса + layer_info.append({ + 'index': index, # Порядковый номер слоя + 'name': layer_name, + 'type': layer_type, + 'weights': layer_weights + }) # Сохранение данных в JSON файл with open(MODEL_DATA_PATH, 'w') as f: - json.dump(layer_weights, f, indent=2) # добавляем отступы для лучшей читаемости + json.dump(layer_info, f, indent=2) print(f"Model data saved to {MODEL_DATA_PATH}") @@ -34,13 +40,13 @@ loaded_model_data = json.load(f) # Преобразование данных обратно в numpy массивы -for layer_name, weights in loaded_model_data.items(): - loaded_model_data[layer_name] = [np.array(w) for w in weights] +for layer_data in loaded_model_data: + layer_data['weights'] = [np.array(w) for w in layer_data['weights']] # Вывод данных -print("Model layers and weights:") -for layer_name, weights in loaded_model_data.items(): - print("Layer:", layer_name) - for weight in weights: +print("Model layers and weights with order:") +for layer_data in loaded_model_data: + print(f"Layer {layer_data['index']} ({layer_data['type']}, {layer_data['name']}):") + for weight in layer_data['weights']: print(weight) print() diff --git a/app/AlexNet/reader_weights_sample.cpp b/app/AlexNet/reader_weights_sample.cpp index 4c41cdcc..76e62655 100644 --- a/app/AlexNet/reader_weights_sample.cpp +++ b/app/AlexNet/reader_weights_sample.cpp @@ -6,13 +6,17 @@ int main() { std::string json_file = MODEL_PATH; json model_data = read_json(json_file); - for (auto& layer : model_data.items()) { - std::string layer_name = layer.key(); - std::cout << "Layer: " << layer_name << std::endl; + for (const auto& layer_data : model_data) { + int layer_index = layer_data["index"]; + std::string layer_name = layer_data["name"]; + std::string layer_type = layer_data["type"]; + + std::cout << "Layer " << layer_index << " (" << layer_type << ", " + << layer_name << "):" << std::endl; try { - Tensor tensor = create_tensor_from_json(layer.value(), Type::kFloat); - std::cout << tensor << std::endl; + Tensor tensor = create_tensor_from_json(layer_data["weights"], Type::kFloat); + // std::cout << tensor << std::endl; } catch (const std::exception& e) { std::cerr << "Error processing layer " << layer_name << ": " << e.what() << std::endl; diff --git a/app/Graph/graph_build.cpp b/app/Graph/graph_build.cpp index cf581849..101bf811 100644 --- a/app/Graph/graph_build.cpp +++ b/app/Graph/graph_build.cpp @@ -8,95 +8,76 @@ #include "layers/PoolingLayer.hpp" #include #include +#include +#include #include "build.hpp" using namespace itlab_2023; +using LayerTemplate = std::variant; -void build_graph(Tensor input) { +void build_graph(Tensor input, Tensor output) { + int number_of_layers; + std::vector layers; std::string json_file = MODEL_PATH; json model_data = read_json(json_file); + for (const auto& layer_data : model_data) { + number_of_layers++; - int number_of_layers; - ConvolutionalLayer conv1; - ConvolutionalLayer conv2; - ConvolutionalLayer conv3; - ConvolutionalLayer conv4; - ConvolutionalLayer conv5; - FCLayer fc1; - FCLayer fc2; - FCLayer fc1; - FCLayer fc4; - + // + std::string layer_type = layer_data["type"]; + Tensor tensor = create_tensor_from_json(layer_data["weights"], Type::kFloat); - for (auto& layer : model_data.items()) { - number_of_layers++; - std::string layer_name = layer.key(); - Tensor tensor = create_tensor_from_json(layer.value(), Type::kFloat); - if (layer_name == "layer_conv_1") { - ConvolutionalLayer conv1(1, 0, 0, tensor); - } - if (layer_name == "layer_conv_2") { - ConvolutionalLayer conv2(1, 0, 0, tensor); - } - if (layer_name == "layer_conv_3") { - ConvolutionalLayer conv3(1, 0, 0, tensor); - } - if (layer_name == "layer_conv_4") { - ConvolutionalLayer conv4(1, 0, 0, tensor); - } - if (layer_name == "layer_conv_5") { - ConvolutionalLayer conv5(1, 0, 0, tensor); + if (layer_type.find("Conv") != std::string::npos) { + Shape shape = tensor.get_shape(); + Tensor tmp_values = make_tensor(tensor.get_values(), shape); + Tensor tmp_bias = + make_tensor(tensor.get_bias(), tensor.get_bias().size()); + layers.emplace_back(1, 0, 0, tmp_values, tmp_bias); } - if (layer_name == "dense") { - FCLayer fc1 (tensor, tensor.get_bias()); - } - if (layer_name == "dense_1") { - FCLayer fc2(tensor, tensor.get_bias()); - } - if (layer_name == "dense_2") { - FCLayer fc3(tensor, tensor.get_bias()); + + if (layer_type.find("Dense") != std::string::npos) { + Tensor tmp_values = make_tensor(tensor.get_values(), tensor.get_shape()); + Tensor tmp_bias = + make_tensor(tensor.get_bias(), tensor.get_bias().size()); + layers.emplace_back(tmp_values, tmp_bias); } - if (layer_name == "layer_conv_4") { - FCLayer fc4(tensor, tensor.get_bias()); + + if (layer_type.find("Pool") != std::string::npos) { + Shape shape = {2, 2}; + layers.emplace_back(shape); } - } + if (layer_type.find("Flatten") != std::string::npos) { + layers.emplace_back(/*construcrtor of flatten*/); + } - Shape sh1({1, 5, 5, 3}); - std::vector vec; - vec.reserve(75); - for (int i = 0; i < 75; ++i) { - vec.push_back(3); + if (layer_type.find("Dropout") != std::string::npos) { + layers.emplace_back(/*construcrtor of dropout*/); + } } Graph graph(number_of_layers); - Tensor output = make_tensor(vec, sh1); InputLayer a1(kNhwc, kNchw, 1, 2); - Shape poolshape = {2, 2}; - //EWLayer a3("linear", 2.0F, 3.0F); - PoolingLayer pool1(poolshape, "average"); - PoolingLayer pool2(poolshape, "average"); - PoolingLayer pool3(poolshape, "average"); - PoolingLayer pool4(poolshape, "average"); - OutputLayer output; - - + //--------------- graph.setInput(a1, input); - graph.makeConnection(a1, conv1); - graph.makeConnection(conv1, pool1); - graph.makeConnection(pool1, conv2); - graph.makeConnection(conv2, pool2); - graph.makeConnection(pool2, conv3); - graph.makeConnection(conv3, conv4); - graph.makeConnection(conv4, conv5); - graph.makeConnection(conv5, pool3); - graph.makeConnection(pool3, /* flatten1*/); - graph.makeConnection(/* flatten1*/, fc1); - graph.makeConnection(fc1, fc2); - graph.makeConnection(fc2, /*dropout*/); - graph.setOutput(/*dropout*/, output); + graph.makeConnection(a1, conv_layers[0]); + graph.makeConnection(conv_layers[0], pooling_layers[0]); + graph.makeConnection(pooling_layers[0], conv_layers[1]); + graph.makeConnection(conv_layers[1], pooling_layers[1]); + graph.makeConnection(pooling_layers[1], conv_layers[2]); + graph.makeConnection(conv_layers[2], conv_layers[3]); + graph.makeConnection(conv_layers[3], conv_layers[4]); + graph.makeConnection(conv_layers[5], pooling_layers[2]); + graph.makeConnection(pooling_layers[2], flatten1); + graph.makeConnection( flatten1, fc_layers[0]); + graph.makeConnection(fc_layers[0], fc_layers[1]); + graph.makeConnection(fc_layers[1], dropout); + graph.setOutput(dropout, output); graph.inference(); + graph.setOutput(/*layers[number_of_layers - 1]*/ , output); + graph.inference(); + //-------------------------------------- std::vector tmp = *output.as(); std::vector tmp_output = softmax(*output.as()); @@ -130,8 +111,16 @@ int main() { } Shape sh({static_cast(count_pic), 227, 227, 3}); Tensor t = make_tensor(res, sh); - Tensor input = t; //////////////////// + Tensor input = t; + + + Shape sh1({1, 5, 5, 3}); + std::vector vec; + vec.reserve(75); + for (int i = 0; i < 75; ++i) { + vec.push_back(3); + } + Tensor output = make_tensor(vec, sh1); - - build_graph(t); + build_graph(input, output); } \ No newline at end of file diff --git a/include/layers/Tensor.hpp b/include/layers/Tensor.hpp index f6c2c71f..998bde1e 100644 --- a/include/layers/Tensor.hpp +++ b/include/layers/Tensor.hpp @@ -106,6 +106,7 @@ class Tensor { } const std::vector& get_bias() const { return bias_; } + const std::vector& get_values() const { return values_; } bool empty() const { return values_.empty(); } auto begin() { return values_.begin(); } diff --git a/src/Weights_Reader/reader_weights.cpp b/src/Weights_Reader/reader_weights.cpp index 4f811665..f2739c4c 100644 --- a/src/Weights_Reader/reader_weights.cpp +++ b/src/Weights_Reader/reader_weights.cpp @@ -49,12 +49,10 @@ void extract_values_without_bias(const json& j, std::vector& values) { if (j.is_array() && !j.empty() && j.back().is_array()) { bias_size = j.back().size(); } - std::cout << "Temp values size: " << temp_values.size() << std::endl; std::cout << "Bias size: " << bias_size << std::endl; if (temp_values.size() >= bias_size) { values.assign(temp_values.begin(), temp_values.end() - bias_size); } - std::cout << "Values size after extraction: " << values.size() << std::endl; } void parse_json_shape(const json& j, std::vector& shape, size_t dim) { @@ -112,7 +110,6 @@ Tensor create_tensor_from_json(const json& j, Type type) { if (expected_size == 1 && shape.empty()) { expected_size = 0; } - std::cout << "Expected size: " << expected_size << std::endl; extract_bias_from_json(j, bias); std::cout << "Extracted bias size: " << bias.size() << std::endl; Shape sh(shape); From b5ac02ea6374f6fee79437c32e6b63dd631b9154 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Tue, 22 Oct 2024 21:24:11 +0300 Subject: [PATCH 03/14] fix name --- app/AlexNet/parser.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/AlexNet/parser.py b/app/AlexNet/parser.py index 84d734a5..9389baef 100644 --- a/app/AlexNet/parser.py +++ b/app/AlexNet/parser.py @@ -7,7 +7,7 @@ # Пути к модели и JSON файлу BASE_DIR = os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__)))) MODEL_PATH = os.path.join(BASE_DIR, 'docs', 'AlexNet-model.h5') -MODEL_DATA_PATH = os.path.join(BASE_DIR, 'docs', 'model_data_alexnet_with_order.json') +MODEL_DATA_PATH = os.path.join(BASE_DIR, 'docs', 'model_data_alexnet_1.json') # Загрузка модели model = load_model(MODEL_PATH) From 6c695bb6bab7f94486468fc64405ccea5bc45ecf Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Wed, 23 Oct 2024 19:28:58 +0300 Subject: [PATCH 04/14] add container --- app/Graph/graph_build.cpp | 48 ++++++++++++++------------------------- 1 file changed, 17 insertions(+), 31 deletions(-) diff --git a/app/Graph/graph_build.cpp b/app/Graph/graph_build.cpp index 101bf811..d47a4c66 100644 --- a/app/Graph/graph_build.cpp +++ b/app/Graph/graph_build.cpp @@ -13,40 +13,34 @@ #include "build.hpp" using namespace itlab_2023; -using LayerTemplate = std::variant; void build_graph(Tensor input, Tensor output) { - int number_of_layers; - std::vector layers; + std::vector> layers; std::string json_file = MODEL_PATH; json model_data = read_json(json_file); for (const auto& layer_data : model_data) { - number_of_layers++; - // std::string layer_type = layer_data["type"]; Tensor tensor = create_tensor_from_json(layer_data["weights"], Type::kFloat); if (layer_type.find("Conv") != std::string::npos) { Shape shape = tensor.get_shape(); Tensor tmp_values = make_tensor(tensor.get_values(), shape); - Tensor tmp_bias = - make_tensor(tensor.get_bias(), tensor.get_bias().size()); - layers.emplace_back(1, 0, 0, tmp_values, tmp_bias); + Tensor tmp_bias = make_tensor(tensor.get_bias()); + layers.push_back(std::make_shared(1, 0, 0, tmp_values, tmp_bias)); } if (layer_type.find("Dense") != std::string::npos) { Tensor tmp_values = make_tensor(tensor.get_values(), tensor.get_shape()); - Tensor tmp_bias = - make_tensor(tensor.get_bias(), tensor.get_bias().size()); - layers.emplace_back(tmp_values, tmp_bias); + Tensor tmp_bias = make_tensor(tensor.get_bias()); + layers.push_back(std::make_shared(tmp_values, tmp_bias)); } if (layer_type.find("Pool") != std::string::npos) { Shape shape = {2, 2}; - layers.emplace_back(shape); + layers.push_back(std::make_shared(shape)); } if (layer_type.find("Flatten") != std::string::npos) { @@ -57,27 +51,20 @@ void build_graph(Tensor input, Tensor output) { layers.emplace_back(/*construcrtor of dropout*/); } } - Graph graph(number_of_layers); + Graph graph(layers.size()); InputLayer a1(kNhwc, kNchw, 1, 2); - //--------------- + graph.setInput(a1, input); - graph.makeConnection(a1, conv_layers[0]); - graph.makeConnection(conv_layers[0], pooling_layers[0]); - graph.makeConnection(pooling_layers[0], conv_layers[1]); - graph.makeConnection(conv_layers[1], pooling_layers[1]); - graph.makeConnection(pooling_layers[1], conv_layers[2]); - graph.makeConnection(conv_layers[2], conv_layers[3]); - graph.makeConnection(conv_layers[3], conv_layers[4]); - graph.makeConnection(conv_layers[5], pooling_layers[2]); - graph.makeConnection(pooling_layers[2], flatten1); - graph.makeConnection( flatten1, fc_layers[0]); - graph.makeConnection(fc_layers[0], fc_layers[1]); - graph.makeConnection(fc_layers[1], dropout); - graph.setOutput(dropout, output); - graph.inference(); - graph.setOutput(/*layers[number_of_layers - 1]*/ , output); + + graph.makeConnection(a1, *layers[0]); + + for (size_t i = 0; i < layers.size() - 1; ++i) { + graph.makeConnection(*layers[i], *layers[i + 1]); + } + + graph.setOutput(*layers.back(), output); + graph.inference(); - //-------------------------------------- std::vector tmp = *output.as(); std::vector tmp_output = softmax(*output.as()); @@ -113,7 +100,6 @@ int main() { Tensor t = make_tensor(res, sh); Tensor input = t; - Shape sh1({1, 5, 5, 3}); std::vector vec; vec.reserve(75); From e912fe7cd3ca670fd6ed35850fb3b5ed05061171 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Wed, 23 Oct 2024 19:34:49 +0300 Subject: [PATCH 05/14] clang --- app/AlexNet/reader_weights_sample.cpp | 3 ++- app/Graph/graph_build.cpp | 17 ++++++++++------- app/ReaderImage/reader_img_s.cpp | 5 +++-- 3 files changed, 15 insertions(+), 10 deletions(-) diff --git a/app/AlexNet/reader_weights_sample.cpp b/app/AlexNet/reader_weights_sample.cpp index 76e62655..4d77c57c 100644 --- a/app/AlexNet/reader_weights_sample.cpp +++ b/app/AlexNet/reader_weights_sample.cpp @@ -15,7 +15,8 @@ int main() { << layer_name << "):" << std::endl; try { - Tensor tensor = create_tensor_from_json(layer_data["weights"], Type::kFloat); + Tensor tensor = + create_tensor_from_json(layer_data["weights"], Type::kFloat); // std::cout << tensor << std::endl; } catch (const std::exception& e) { std::cerr << "Error processing layer " << layer_name << ": " << e.what() diff --git a/app/Graph/graph_build.cpp b/app/Graph/graph_build.cpp index d47a4c66..48577e78 100644 --- a/app/Graph/graph_build.cpp +++ b/app/Graph/graph_build.cpp @@ -1,4 +1,10 @@ +#include +#include +#include +#include + #include "Weights_Reader/reader_weights.hpp" +#include "build.hpp" #include "graph/graph.hpp" #include "layers/ConvLayer.hpp" #include "layers/EWLayer.hpp" @@ -6,11 +12,6 @@ #include "layers/InputLayer.hpp" #include "layers/OutputLayer.hpp" #include "layers/PoolingLayer.hpp" -#include -#include -#include -#include -#include "build.hpp" using namespace itlab_2023; @@ -23,13 +24,15 @@ void build_graph(Tensor input, Tensor output) { for (const auto& layer_data : model_data) { std::string layer_type = layer_data["type"]; - Tensor tensor = create_tensor_from_json(layer_data["weights"], Type::kFloat); + Tensor tensor = + create_tensor_from_json(layer_data["weights"], Type::kFloat); if (layer_type.find("Conv") != std::string::npos) { Shape shape = tensor.get_shape(); Tensor tmp_values = make_tensor(tensor.get_values(), shape); Tensor tmp_bias = make_tensor(tensor.get_bias()); - layers.push_back(std::make_shared(1, 0, 0, tmp_values, tmp_bias)); + layers.push_back( + std::make_shared(1, 0, 0, tmp_values, tmp_bias)); } if (layer_type.find("Dense") != std::string::npos) { diff --git a/app/ReaderImage/reader_img_s.cpp b/app/ReaderImage/reader_img_s.cpp index b370efc6..7c7d804a 100644 --- a/app/ReaderImage/reader_img_s.cpp +++ b/app/ReaderImage/reader_img_s.cpp @@ -1,5 +1,6 @@ -#include "reader_img.hpp" -#include +#include + +#include "reader_img.hpp" using namespace cv; void read(std::string& path) { Mat image = imread(path); From 46dd5a75d5fb0532cce70d28e59d95c8470fe351 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Mon, 28 Oct 2024 10:36:02 +0300 Subject: [PATCH 06/14] add LayerType --- app/Graph/graph_build.cpp | 34 ++++++++++++++++++++++++---------- include/graph/graph.hpp | 30 +++++++++++++++++++++++++++--- include/layers/Layer.hpp | 1 + 3 files changed, 52 insertions(+), 13 deletions(-) diff --git a/app/Graph/graph_build.cpp b/app/Graph/graph_build.cpp index a1d474c7..322bc63a 100644 --- a/app/Graph/graph_build.cpp +++ b/app/Graph/graph_build.cpp @@ -43,9 +43,10 @@ void build_graph(Tensor input, Tensor output) { Tensor tmp_values = tensor; Tensor tmp_bias = make_tensor(tensor.get_bias()); - - layers.push_back( - std::make_shared(1, 0, 0, tmp_values, tmp_bias)); + auto conv_layer = + std::make_shared(1, 0, 0, tmp_values, tmp_bias); + conv_layer->setName(kConvolution); + layers.push_back(conv_layer); std::cout << "ConvLayer added to layers." << std::endl; } @@ -53,7 +54,9 @@ void build_graph(Tensor input, Tensor output) { Tensor tmp_values = tensor; Tensor tmp_bias = make_tensor(tensor.get_bias()); - layers.push_back(std::make_shared(tmp_values, tmp_bias)); + auto fc_layer = std::make_shared(tmp_values, tmp_bias); + fc_layer->setName(kFullyConnected); + layers.push_back(fc_layer); std::cout << "DenseLayer added to layers." << std::endl; } @@ -61,25 +64,31 @@ void build_graph(Tensor input, Tensor output) { Shape shape = {2, 2}; std::cout << "PoolingLayer shape: " << shape[0] << "x" << shape[1] << std::endl; - - layers.push_back(std::make_shared(shape)); + auto pool_layer = std::make_shared(shape); + pool_layer->setName(kPooling); + layers.push_back(pool_layer); std::cout << "PoolingLayer added to layers." << std::endl; } if (layer_type.find("Flatten") != std::string::npos) { - layers.emplace_back(std::make_shared()); + auto flatten_layer = std::make_shared(); + flatten_layer->setName(kFlatten); + layers.push_back(flatten_layer); std::cout << "FlattenLayer added to layers." << std::endl; } if (layer_type.find("Dropout") != std::string::npos) { - layers.emplace_back(std::make_shared(0.5)); + auto dropout_layer = std::make_shared(0.5); + dropout_layer->setName(kDropout); + layers.push_back(dropout_layer); std::cout << "DropOutLayer added to layers with probability 0.5." << std::endl; } } - + std::cout << "number of layers - " << layers.size() + 1<< std::endl; Graph graph(static_cast(layers.size())); InputLayer a1(kNhwc, kNchw, 1, 2); + std::cout << "InputLayer created." << std::endl; graph.setInput(a1, input); @@ -91,10 +100,15 @@ void build_graph(Tensor input, Tensor output) { for (size_t i = 0; i < layers.size() - 1; ++i) { graph.makeConnection(*layers[i], *layers[i + 1]); - std::cout << "Connection made between layer " << i << " and layer " << i + 1 + std::cout << "Connection made between layer " << i << " (" + << layerTypeToString(layers[i]->getName()) << ")" + << " and layer " << i + 1 << " (" + << layerTypeToString(layers[i + 1]->getName()) << ")" << std::endl; } + + graph.setOutput(*layers.back(), output); std::cout << "Output set in graph." << std::endl; diff --git a/include/graph/graph.hpp b/include/graph/graph.hpp index d72e70e5..5c1a18a9 100644 --- a/include/graph/graph.hpp +++ b/include/graph/graph.hpp @@ -10,7 +10,30 @@ #include "layers/Layer.hpp" namespace itlab_2023 { - +std::string layerTypeToString(LayerType type) { + switch (type) { + case kInput: + return "Input"; + case kPooling: + return "Pooling"; + case kNormalization: + return "Normalization"; + case kDropout: + return "Dropout"; + case kElementWise: + return "ElementWise"; + case kConvolution: + return "Convolution"; + case kFullyConnected: + return "FullyConnected"; + case kFlatten: + return "Flatten"; + case kOutput: + return "Output"; + default: + return "Unknown"; + } +} class Graph { int BiggestSize_; int V_; @@ -108,8 +131,9 @@ class Graph { #ifdef ENABLE_STATISTIC_TIME auto start = std::chrono::high_resolution_clock::now(); #endif - std::cout << "Running layer " << i - << " with input shape: " << inten_.get_shape() + std::cout << "Running layer " << i << " (" + << layerTypeToString(layers_[i]->getName()) << ") " + << "with input shape: " << inten_.get_shape() << ", output shape: " << outten_->get_shape() << std::endl; layers_[i]->run(inten_, *outten_); diff --git a/include/layers/Layer.hpp b/include/layers/Layer.hpp index 5c84a7c7..1238f0ef 100644 --- a/include/layers/Layer.hpp +++ b/include/layers/Layer.hpp @@ -18,6 +18,7 @@ enum LayerType { kElementWise, kConvolution, kFullyConnected, + kFlatten, kOutput, }; From d95d3b6b2638a9241670f225417fb15f1b83cf02 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 12:24:48 +0300 Subject: [PATCH 07/14] inference completed --- app/Graph/build.cpp | 131 +++++++++++++++++++- app/Graph/build.hpp | 16 ++- app/Graph/graph_build.cpp | 144 ++-------------------- include/Weights_Reader/reader_weights.hpp | 2 +- include/graph/graph.hpp | 42 +------ include/layers/Shape.hpp | 5 +- src/Weights_Reader/reader_weights.cpp | 2 +- 7 files changed, 163 insertions(+), 179 deletions(-) diff --git a/app/Graph/build.cpp b/app/Graph/build.cpp index f7b3fddd..572620ec 100644 --- a/app/Graph/build.cpp +++ b/app/Graph/build.cpp @@ -1,3 +1,132 @@ #include "build.hpp" -#include \ No newline at end of file +void build_graph(Tensor input, Tensor output) { + std::vector> layers; + + std::string json_file = MODEL_PATH; + json model_data = read_json(json_file); + + std::cout << "Loaded model data from JSON." << std::endl; + + for (const auto& layer_data : model_data) { + std::string layer_type = layer_data["type"]; + std::cout << "Processing layer of type: " << layer_type << std::endl; + + Tensor tensor = + create_tensor_from_json(layer_data["weights"], Type::kFloat); + + if (layer_type.find("Conv") != std::string::npos) { + Shape shape = tensor.get_shape(); + std::cout << "PoolingLayer shape: "; + for (size_t i = 0; i < shape.dims(); ++i) { + std::cout << shape[i] << " "; + } + std::cout << std::endl; + + Tensor tmp_values = tensor; + Tensor tmp_bias = make_tensor(tensor.get_bias()); + + auto conv_layer = + std::make_shared(1, 0, 1, tmp_values, tmp_bias); + conv_layer->setName(kConvolution); + layers.push_back(conv_layer); + std::cout << "ConvLayer added to layers." << std::endl; + } + + if (layer_type.find("Dense") != std::string::npos) { + Tensor tmp_values = tensor; + std::vector Values_vector = *tensor.as(); + std::vector> Values_vector_2d( + tensor.get_shape()[0], + std::vector(tensor.get_shape()[1], 0.0f)); + int q = 0; + for (int i = 0; i < Values_vector.size(); i++) { + Values_vector_2d[q][i - (q * tensor.get_shape()[1])] = Values_vector[i]; + if ((i + 1) % tensor.get_shape()[1] == 0) { + q++; + } + } + std::vector> Values_vector_2d_2( + tensor.get_shape()[1], + std::vector(tensor.get_shape()[0], 0.0f)); + + for (int i = 0; i < tensor.get_shape()[0]; ++i) { + for (int j = 0; j < tensor.get_shape()[1]; ++j) { + Values_vector_2d_2[j][i] = Values_vector_2d[i][j]; + } + } + std::vector Values_vector_1d( + tensor.get_shape()[0] * tensor.get_shape()[1], 0.0f); + int index_1d = 0; + + for (int j = 0; j < tensor.get_shape()[1]; ++j) { + for (int k = 0; k < tensor.get_shape()[0]; ++k) { + Values_vector_1d[index_1d++] = Values_vector_2d_2[j][k]; + } + } + + Shape shape_fc({tensor.get_shape()[1], tensor.get_shape()[0]}); + Tensor values = make_tensor(Values_vector_1d, shape_fc); + Tensor tmp_bias = make_tensor(tensor.get_bias()); + + auto fc_layer = std::make_shared(values, tmp_bias); + fc_layer->setName(kFullyConnected); + layers.push_back(fc_layer); + std::cout << "DenseLayer added to layers." << std::endl; + } + + if (layer_type.find("Pool") != std::string::npos) { + Shape shape = {2, 2}; + std::cout << "PoolingLayer shape: " << shape[0] << "x" << shape[1] + << std::endl; + auto pool_layer = std::make_shared(shape); + pool_layer->setName(kPooling); + layers.push_back(pool_layer); + std::cout << "PoolingLayer added to layers." << std::endl; + } + + if (layer_type.find("Flatten") != std::string::npos) { + auto flatten_layer = std::make_shared(); + flatten_layer->setName(kFlatten); + layers.push_back(flatten_layer); + std::cout << "FlattenLayer added to layers." << std::endl; + } + + if (layer_type.find("Dropout") != std::string::npos) { + auto dropout_layer = std::make_shared(0.5); + dropout_layer->setName(kDropout); + layers.push_back(dropout_layer); + std::cout << "DropOutLayer added to layers with probability 0.5." + << std::endl; + } + } + std::cout << "number of layers - " << layers.size() + 1 << std::endl; + Graph graph(static_cast(layers.size())); + InputLayer a1(kNhwc, kNchw, 1, 2); + + std::cout << "InputLayer created." << std::endl; + + graph.setInput(a1, input); + std::cout << "Input set in graph." << std::endl; + + graph.makeConnection(a1, *layers[0]); + std::cout << "Connection made between InputLayer and first layer." + << std::endl; + + for (size_t i = 0; i < layers.size() - 1; ++i) { + graph.makeConnection(*layers[i], *layers[i + 1]); + } + + graph.setOutput(*layers.back(), output); + std::cout << "Output set in graph." << std::endl; + + std::cout << "Starting inference..." << std::endl; + graph.inference(); + std::cout << "Inference completed." << std::endl; + + std::vector tmp = *output.as(); + std::vector tmp_output = softmax(*output.as()); + for (float i : tmp) { + std::cout << i << " "; + } +} \ No newline at end of file diff --git a/app/Graph/build.hpp b/app/Graph/build.hpp index d552a851..209108eb 100644 --- a/app/Graph/build.hpp +++ b/app/Graph/build.hpp @@ -1,3 +1,17 @@ -#pragma once #include +#include +#include +#include #include +#include "Weights_Reader/reader_weights.hpp" +#include "graph/graph.hpp" +#include "layers/ConvLayer.hpp" +#include "layers/DropOutLayer.hpp" +#include "layers/EWLayer.hpp" +#include "layers/FCLayer.hpp" +#include "layers/FlattenLayer.hpp" +#include "layers/InputLayer.hpp" +#include "layers/OutputLayer.hpp" +#include "layers/PoolingLayer.hpp" + +void build_graph(Tensor input, Tensor output); \ No newline at end of file diff --git a/app/Graph/graph_build.cpp b/app/Graph/graph_build.cpp index 322bc63a..6bf353ea 100644 --- a/app/Graph/graph_build.cpp +++ b/app/Graph/graph_build.cpp @@ -1,128 +1,8 @@ -#include -#include -#include -#include - -#include "Weights_Reader/reader_weights.hpp" #include "build.hpp" -#include "graph/graph.hpp" -#include "layers/ConvLayer.hpp" -#include "layers/DropOutLayer.hpp" -#include "layers/EWLayer.hpp" -#include "layers/FCLayer.hpp" -#include "layers/FlattenLayer.hpp" -#include "layers/InputLayer.hpp" -#include "layers/OutputLayer.hpp" -#include "layers/PoolingLayer.hpp" +#include "build.cpp" using namespace itlab_2023; -void build_graph(Tensor input, Tensor output) { - std::vector> layers; - - std::string json_file = MODEL_PATH; - json model_data = read_json(json_file); - - std::cout << "Loaded model data from JSON." << std::endl; - - for (const auto& layer_data : model_data) { - std::string layer_type = layer_data["type"]; - std::cout << "Processing layer of type: " << layer_type << std::endl; - - Tensor tensor = - create_tensor_from_json(layer_data["weights"], Type::kFloat); - - if (layer_type.find("Conv") != std::string::npos) { - Shape shape = tensor.get_shape(); - std::cout << "PoolingLayer shape: "; - for (size_t i = 0; i < shape.dims(); ++i) { - std::cout << shape[i] << " "; - } - std::cout << std::endl; - - Tensor tmp_values = tensor; - Tensor tmp_bias = make_tensor(tensor.get_bias()); - - auto conv_layer = - std::make_shared(1, 0, 0, tmp_values, tmp_bias); - conv_layer->setName(kConvolution); - layers.push_back(conv_layer); - std::cout << "ConvLayer added to layers." << std::endl; - } - - if (layer_type.find("Dense") != std::string::npos) { - Tensor tmp_values = tensor; - Tensor tmp_bias = make_tensor(tensor.get_bias()); - - auto fc_layer = std::make_shared(tmp_values, tmp_bias); - fc_layer->setName(kFullyConnected); - layers.push_back(fc_layer); - std::cout << "DenseLayer added to layers." << std::endl; - } - - if (layer_type.find("Pool") != std::string::npos) { - Shape shape = {2, 2}; - std::cout << "PoolingLayer shape: " << shape[0] << "x" << shape[1] - << std::endl; - auto pool_layer = std::make_shared(shape); - pool_layer->setName(kPooling); - layers.push_back(pool_layer); - std::cout << "PoolingLayer added to layers." << std::endl; - } - - if (layer_type.find("Flatten") != std::string::npos) { - auto flatten_layer = std::make_shared(); - flatten_layer->setName(kFlatten); - layers.push_back(flatten_layer); - std::cout << "FlattenLayer added to layers." << std::endl; - } - - if (layer_type.find("Dropout") != std::string::npos) { - auto dropout_layer = std::make_shared(0.5); - dropout_layer->setName(kDropout); - layers.push_back(dropout_layer); - std::cout << "DropOutLayer added to layers with probability 0.5." - << std::endl; - } - } - std::cout << "number of layers - " << layers.size() + 1<< std::endl; - Graph graph(static_cast(layers.size())); - InputLayer a1(kNhwc, kNchw, 1, 2); - - std::cout << "InputLayer created." << std::endl; - - graph.setInput(a1, input); - std::cout << "Input set in graph." << std::endl; - - graph.makeConnection(a1, *layers[0]); - std::cout << "Connection made between InputLayer and first layer." - << std::endl; - - for (size_t i = 0; i < layers.size() - 1; ++i) { - graph.makeConnection(*layers[i], *layers[i + 1]); - std::cout << "Connection made between layer " << i << " (" - << layerTypeToString(layers[i]->getName()) << ")" - << " and layer " << i + 1 << " (" - << layerTypeToString(layers[i + 1]->getName()) << ")" - << std::endl; - } - - - - graph.setOutput(*layers.back(), output); - std::cout << "Output set in graph." << std::endl; - - std::cout << "Starting inference..." << std::endl; - graph.inference(); - std::cout << "Inference completed." << std::endl; - - std::vector tmp = *output.as(); - std::vector tmp_output = softmax(*output.as()); - for (float i : tmp) { - std::cout << i << " "; - } -} - int main() { std::string image_path = IMAGE1_PATH; cv::Mat image = cv::imread(image_path); @@ -130,23 +10,21 @@ int main() { throw std::runtime_error("Failed to load image"); } cv::Mat resized_image; - cv::resize(image, resized_image, cv::Size(227, 227)); + cv::cvtColor(image, image, cv::COLOR_BGR2GRAY); + cv::resize(image, resized_image, cv::Size(28, 28)); std::vector channels; + cv::split(resized_image, channels); + int count_pic = 1; - std::vector res(count_pic * 227 * 227 * 3); - int c = 0; - for (int i = 0; i < 227; ++i) { - for (int j = 0; j < 227; ++j) { - res[c] = channels[2].at(i, j); - c++; - res[c] = channels[1].at(i, j); - c++; - res[c] = channels[0].at(i, j); - c++; + std::vector res(count_pic * 28 * 28); + + for (int i = 0; i < 28; ++i) { + for (int j = 0; j < 28; ++j) { + res[i * 28 + j] = channels[0].at(i,j); } } - Shape sh({static_cast(count_pic), 227, 227, 3}); + Shape sh({static_cast(count_pic), 28, 28, 1}); Tensor t = make_tensor(res, sh); Tensor input = t; diff --git a/include/Weights_Reader/reader_weights.hpp b/include/Weights_Reader/reader_weights.hpp index 34eecfd3..f9c7fa16 100644 --- a/include/Weights_Reader/reader_weights.hpp +++ b/include/Weights_Reader/reader_weights.hpp @@ -11,6 +11,6 @@ json read_json(const std::string& filename); void extract_values_without_bias(const json& j, std::vector& values); void extract_values_from_json(const json& j, std::vector& values); void parse_json_shape(const json& j, std::vector& shape, - size_t dim = 0); + size_t dim); Tensor create_tensor_from_json(const json& j, Type type); void extract_bias_from_json(const json& j, std::vector& bias); diff --git a/include/graph/graph.hpp b/include/graph/graph.hpp index 5c1a18a9..e129a516 100644 --- a/include/graph/graph.hpp +++ b/include/graph/graph.hpp @@ -1,3 +1,4 @@ + #pragma once #include #include @@ -10,30 +11,7 @@ #include "layers/Layer.hpp" namespace itlab_2023 { -std::string layerTypeToString(LayerType type) { - switch (type) { - case kInput: - return "Input"; - case kPooling: - return "Pooling"; - case kNormalization: - return "Normalization"; - case kDropout: - return "Dropout"; - case kElementWise: - return "ElementWise"; - case kConvolution: - return "Convolution"; - case kFullyConnected: - return "FullyConnected"; - case kFlatten: - return "Flatten"; - case kOutput: - return "Output"; - default: - return "Unknown"; - } -} + class Graph { int BiggestSize_; int V_; @@ -102,11 +80,9 @@ class Graph { std::vector traversal; q.push(start_); visited[start_] = true; - while (!q.empty()) { int current = q.front(); q.pop(); - if (current == end_) { int node = current; while (node != -1) { @@ -116,7 +92,6 @@ class Graph { std::reverse(traversal.begin(), traversal.end()); break; } - for (int ind = arrayV_[current]; ind < arrayV_[current + 1]; ind++) { int neighbor = arrayE_[ind]; if (!visited[neighbor]) { @@ -126,40 +101,27 @@ class Graph { } } } - for (int i : traversal) { #ifdef ENABLE_STATISTIC_TIME auto start = std::chrono::high_resolution_clock::now(); #endif - std::cout << "Running layer " << i << " (" - << layerTypeToString(layers_[i]->getName()) << ") " - << "with input shape: " << inten_.get_shape() - << ", output shape: " << outten_->get_shape() << std::endl; - layers_[i]->run(inten_, *outten_); - #ifdef ENABLE_STATISTIC_TENSORS tensors_.push_back(inten_); tensors_.push_back(*outten_); #endif - #ifdef ENABLE_STATISTIC_WEIGHTS weights_.push_back(layers_[i]->get_weights()); #endif - inten_ = *outten_; - #ifdef ENABLE_STATISTIC_TIME auto end = std::chrono::high_resolution_clock::now(); auto elapsed = std::chrono::duration_cast(end - start); time_.push_back(static_cast(elapsed.count())); - std::cout << "Layer " << i << " execution time: " << elapsed.count() - << " ms" << std::endl; #endif } } - void setOutput(const Layer& lay, Tensor& vec) { end_ = lay.getID(); outten_ = &vec; diff --git a/include/layers/Shape.hpp b/include/layers/Shape.hpp index 26418cb8..693a1512 100644 --- a/include/layers/Shape.hpp +++ b/include/layers/Shape.hpp @@ -1,10 +1,10 @@ #pragma once -#include -#include #include #include +#include #include +#include #include #include @@ -40,6 +40,7 @@ class Shape { size_t dims() const noexcept { return dims_.size(); } size_t get_index(const std::vector& coords) const; friend std::ostream& operator<<(std::ostream& os, const Shape& shape); + private: std::vector dims_; }; diff --git a/src/Weights_Reader/reader_weights.cpp b/src/Weights_Reader/reader_weights.cpp index f2739c4c..d41ad1ce 100644 --- a/src/Weights_Reader/reader_weights.cpp +++ b/src/Weights_Reader/reader_weights.cpp @@ -55,7 +55,7 @@ void extract_values_without_bias(const json& j, std::vector& values) { } } -void parse_json_shape(const json& j, std::vector& shape, size_t dim) { +void parse_json_shape(const json& j, std::vector& shape, size_t dim = 0) { if (dim == 0) { if (j.is_array()) { if (j.empty()) { From f935fa331a188f3789303db2924c53dc55aeebf0 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 12:51:47 +0300 Subject: [PATCH 08/14] fix size_t and dims --- app/Graph/build.cpp | 10 +++++----- app/Graph/build.hpp | 3 ++- app/Graph/graph_build.cpp | 6 +++--- include/Weights_Reader/reader_weights.hpp | 3 +-- src/Weights_Reader/reader_weights.cpp | 5 +++-- 5 files changed, 14 insertions(+), 13 deletions(-) diff --git a/app/Graph/build.cpp b/app/Graph/build.cpp index 572620ec..381c74aa 100644 --- a/app/Graph/build.cpp +++ b/app/Graph/build.cpp @@ -40,7 +40,7 @@ void build_graph(Tensor input, Tensor output) { tensor.get_shape()[0], std::vector(tensor.get_shape()[1], 0.0f)); int q = 0; - for (int i = 0; i < Values_vector.size(); i++) { + for (size_t i = 0; i < Values_vector.size(); i++) { Values_vector_2d[q][i - (q * tensor.get_shape()[1])] = Values_vector[i]; if ((i + 1) % tensor.get_shape()[1] == 0) { q++; @@ -50,8 +50,8 @@ void build_graph(Tensor input, Tensor output) { tensor.get_shape()[1], std::vector(tensor.get_shape()[0], 0.0f)); - for (int i = 0; i < tensor.get_shape()[0]; ++i) { - for (int j = 0; j < tensor.get_shape()[1]; ++j) { + for (size_t i = 0; i < tensor.get_shape()[0]; ++i) { + for (size_t j = 0; j < tensor.get_shape()[1]; ++j) { Values_vector_2d_2[j][i] = Values_vector_2d[i][j]; } } @@ -59,8 +59,8 @@ void build_graph(Tensor input, Tensor output) { tensor.get_shape()[0] * tensor.get_shape()[1], 0.0f); int index_1d = 0; - for (int j = 0; j < tensor.get_shape()[1]; ++j) { - for (int k = 0; k < tensor.get_shape()[0]; ++k) { + for (size_t j = 0; j < tensor.get_shape()[1]; ++j) { + for (size_t k = 0; k < tensor.get_shape()[0]; ++k) { Values_vector_1d[index_1d++] = Values_vector_2d_2[j][k]; } } diff --git a/app/Graph/build.hpp b/app/Graph/build.hpp index 209108eb..ca95f8a0 100644 --- a/app/Graph/build.hpp +++ b/app/Graph/build.hpp @@ -1,8 +1,9 @@ #include +#include #include #include #include -#include + #include "Weights_Reader/reader_weights.hpp" #include "graph/graph.hpp" #include "layers/ConvLayer.hpp" diff --git a/app/Graph/graph_build.cpp b/app/Graph/graph_build.cpp index 6bf353ea..7949b23f 100644 --- a/app/Graph/graph_build.cpp +++ b/app/Graph/graph_build.cpp @@ -1,5 +1,5 @@ -#include "build.hpp" #include "build.cpp" +#include "build.hpp" using namespace itlab_2023; @@ -13,7 +13,7 @@ int main() { cv::cvtColor(image, image, cv::COLOR_BGR2GRAY); cv::resize(image, resized_image, cv::Size(28, 28)); std::vector channels; - + cv::split(resized_image, channels); int count_pic = 1; @@ -21,7 +21,7 @@ int main() { for (int i = 0; i < 28; ++i) { for (int j = 0; j < 28; ++j) { - res[i * 28 + j] = channels[0].at(i,j); + res[i * 28 + j] = channels[0].at(i, j); } } Shape sh({static_cast(count_pic), 28, 28, 1}); diff --git a/include/Weights_Reader/reader_weights.hpp b/include/Weights_Reader/reader_weights.hpp index f9c7fa16..e31e0138 100644 --- a/include/Weights_Reader/reader_weights.hpp +++ b/include/Weights_Reader/reader_weights.hpp @@ -10,7 +10,6 @@ using namespace itlab_2023; json read_json(const std::string& filename); void extract_values_without_bias(const json& j, std::vector& values); void extract_values_from_json(const json& j, std::vector& values); -void parse_json_shape(const json& j, std::vector& shape, - size_t dim); +void parse_json_shape(const json& j, std::vector& shape, size_t dim); Tensor create_tensor_from_json(const json& j, Type type); void extract_bias_from_json(const json& j, std::vector& bias); diff --git a/src/Weights_Reader/reader_weights.cpp b/src/Weights_Reader/reader_weights.cpp index d41ad1ce..7c697a7d 100644 --- a/src/Weights_Reader/reader_weights.cpp +++ b/src/Weights_Reader/reader_weights.cpp @@ -55,7 +55,8 @@ void extract_values_without_bias(const json& j, std::vector& values) { } } -void parse_json_shape(const json& j, std::vector& shape, size_t dim = 0) { +void parse_json_shape(const json& j, std::vector& shape, + size_t dim) { if (dim == 0) { if (j.is_array()) { if (j.empty()) { @@ -98,7 +99,7 @@ Tensor create_tensor_from_json(const json& j, Type type) { extract_values_without_bias(j, vals); std::cout << "Extracted values size: " << vals.size() << std::endl; - parse_json_shape(j, shape); + parse_json_shape(j, shape, 0); std::cout << "Parsed shape: "; size_t expected_size = 1; for (const auto& dim : shape) { From c059a7e799ee92ebb8d6460f290e25e41f9ca2ee Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 12:55:27 +0300 Subject: [PATCH 09/14] clang --- src/Weights_Reader/reader_weights.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/Weights_Reader/reader_weights.cpp b/src/Weights_Reader/reader_weights.cpp index 7c697a7d..31117feb 100644 --- a/src/Weights_Reader/reader_weights.cpp +++ b/src/Weights_Reader/reader_weights.cpp @@ -55,8 +55,7 @@ void extract_values_without_bias(const json& j, std::vector& values) { } } -void parse_json_shape(const json& j, std::vector& shape, - size_t dim) { +void parse_json_shape(const json& j, std::vector& shape, size_t dim) { if (dim == 0) { if (j.is_array()) { if (j.empty()) { From 582cda1f8195f2518a4b2c7e621b5e8d78257c20 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 13:10:42 +0300 Subject: [PATCH 10/14] fix dims in test: --- test/model_read/model_read.cpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/test/model_read/model_read.cpp b/test/model_read/model_read.cpp index a2b8e71a..19701a09 100644 --- a/test/model_read/model_read.cpp +++ b/test/model_read/model_read.cpp @@ -68,7 +68,7 @@ TEST(ExtractValuesFromJsonTests, HandlesNestedArray) { TEST(ParseJsonShapeTests, HandlesEmptyArray) { json j = json::array({}); std::vector shape; - parse_json_shape(j, shape); + parse_json_shape(j, shape, 0); std::vector expected = {0}; EXPECT_EQ(shape, expected); } @@ -76,7 +76,7 @@ TEST(ParseJsonShapeTests, HandlesEmptyArray) { TEST(ParseJsonShapeTests, HandlesSimpleArray) { json j = json::array({{1.0, 2.0, 3.0}, {1.0, 2.0, 3.0}}); std::vector shape; - parse_json_shape(j, shape); + parse_json_shape(j, shape, 0); std::vector expected = {3}; EXPECT_EQ(shape, expected); } @@ -84,7 +84,7 @@ TEST(ParseJsonShapeTests, HandlesSimpleArray) { TEST(ParseJsonShapeTests, HandlesNestedArray) { json j = json::array({{{1.0, 2.0}, {3.0, 4.0}}, {3.0, 4.0}}); std::vector shape; - parse_json_shape(j, shape); + parse_json_shape(j, shape, 0); std::vector expected = {2, 2}; EXPECT_EQ(shape, expected); } @@ -157,7 +157,7 @@ TEST(CreateTensorFromJsonTest, SimpleTensorCheckNoBias) { TEST(CreateTensorFromJsonTest, EmptyShape) { json j = json::array({}); std::vector shape; - parse_json_shape(j, shape); + parse_json_shape(j, shape, 0); std::vector expected = {0}; EXPECT_EQ(shape, expected); } @@ -171,7 +171,7 @@ TEST(ParseJsonShapeTests, HandlesNonArrayJson) { json j = "not_an_array"; std::vector shape; - parse_json_shape(j, shape); + parse_json_shape(j, shape, 0); std::vector expected = {0}; EXPECT_EQ(shape, expected); From 142704ea1c24830ee53889682069810b9116b744 Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 13:32:46 +0300 Subject: [PATCH 11/14] add destructor --- include/layers/Layer.hpp | 1 + 1 file changed, 1 insertion(+) diff --git a/include/layers/Layer.hpp b/include/layers/Layer.hpp index 1238f0ef..a7bcd85c 100644 --- a/include/layers/Layer.hpp +++ b/include/layers/Layer.hpp @@ -25,6 +25,7 @@ enum LayerType { class Layer { public: Layer() = default; + virtual ~Layer() = default; int getID() const { return id_; } void setID(int id) { id_ = id; } LayerType getName() const { return type_; } From dbdbb4698d545c14828589bf6da571f625aa39dc Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 14:15:45 +0300 Subject: [PATCH 12/14] tidy --- app/Graph/build.cpp | 22 +++++++++++----------- app/Graph/build.hpp | 2 +- src/Weights_Reader/reader_weights.cpp | 3 --- 3 files changed, 12 insertions(+), 15 deletions(-) diff --git a/app/Graph/build.cpp b/app/Graph/build.cpp index 381c74aa..e879503a 100644 --- a/app/Graph/build.cpp +++ b/app/Graph/build.cpp @@ -1,6 +1,6 @@ #include "build.hpp" -void build_graph(Tensor input, Tensor output) { +void build_graph(Tensor& input, Tensor& output) { std::vector> layers; std::string json_file = MODEL_PATH; @@ -35,38 +35,38 @@ void build_graph(Tensor input, Tensor output) { if (layer_type.find("Dense") != std::string::npos) { Tensor tmp_values = tensor; - std::vector Values_vector = *tensor.as(); - std::vector> Values_vector_2d( + std::vector values_vector = *tensor.as(); + std::vector> values_vector_2d( tensor.get_shape()[0], std::vector(tensor.get_shape()[1], 0.0f)); int q = 0; - for (size_t i = 0; i < Values_vector.size(); i++) { - Values_vector_2d[q][i - (q * tensor.get_shape()[1])] = Values_vector[i]; + for (size_t i = 0; i < values_vector.size(); i++) { + values_vector_2d[q][i - (q * tensor.get_shape()[1])] = values_vector[i]; if ((i + 1) % tensor.get_shape()[1] == 0) { q++; } } - std::vector> Values_vector_2d_2( + std::vector> values_vector_2d_2( tensor.get_shape()[1], std::vector(tensor.get_shape()[0], 0.0f)); for (size_t i = 0; i < tensor.get_shape()[0]; ++i) { for (size_t j = 0; j < tensor.get_shape()[1]; ++j) { - Values_vector_2d_2[j][i] = Values_vector_2d[i][j]; + values_vector_2d_2[j][i] = values_vector_2d[i][j]; } } - std::vector Values_vector_1d( - tensor.get_shape()[0] * tensor.get_shape()[1], 0.0f); + std::vector values_vector_1d( + tensor.get_shape()[0] * tensor.get_shape()[1], 0.0F); int index_1d = 0; for (size_t j = 0; j < tensor.get_shape()[1]; ++j) { for (size_t k = 0; k < tensor.get_shape()[0]; ++k) { - Values_vector_1d[index_1d++] = Values_vector_2d_2[j][k]; + values_vector_1d[index_1d++] = values_vector_2d_2[j][k]; } } Shape shape_fc({tensor.get_shape()[1], tensor.get_shape()[0]}); - Tensor values = make_tensor(Values_vector_1d, shape_fc); + Tensor values = make_tensor(values_vector_1d, shape_fc); Tensor tmp_bias = make_tensor(tensor.get_bias()); auto fc_layer = std::make_shared(values, tmp_bias); diff --git a/app/Graph/build.hpp b/app/Graph/build.hpp index ca95f8a0..fb5a82bf 100644 --- a/app/Graph/build.hpp +++ b/app/Graph/build.hpp @@ -15,4 +15,4 @@ #include "layers/OutputLayer.hpp" #include "layers/PoolingLayer.hpp" -void build_graph(Tensor input, Tensor output); \ No newline at end of file +void build_graph(Tensor& input, Tensor& output); \ No newline at end of file diff --git a/src/Weights_Reader/reader_weights.cpp b/src/Weights_Reader/reader_weights.cpp index 31117feb..8f67f6b9 100644 --- a/src/Weights_Reader/reader_weights.cpp +++ b/src/Weights_Reader/reader_weights.cpp @@ -107,9 +107,6 @@ Tensor create_tensor_from_json(const json& j, Type type) { } std::cout << std::endl; - if (expected_size == 1 && shape.empty()) { - expected_size = 0; - } extract_bias_from_json(j, bias); std::cout << "Extracted bias size: " << bias.size() << std::endl; Shape sh(shape); From 6d0696e5ade00c8b8301d0c432d334322fd475bd Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 14:23:50 +0300 Subject: [PATCH 13/14] fix expected_size --- src/Weights_Reader/reader_weights.cpp | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/src/Weights_Reader/reader_weights.cpp b/src/Weights_Reader/reader_weights.cpp index 8f67f6b9..938da566 100644 --- a/src/Weights_Reader/reader_weights.cpp +++ b/src/Weights_Reader/reader_weights.cpp @@ -99,12 +99,7 @@ Tensor create_tensor_from_json(const json& j, Type type) { std::cout << "Extracted values size: " << vals.size() << std::endl; parse_json_shape(j, shape, 0); - std::cout << "Parsed shape: "; - size_t expected_size = 1; - for (const auto& dim : shape) { - std::cout << dim << " "; - expected_size *= dim; - } + std::cout << std::endl; extract_bias_from_json(j, bias); From b3b27ac1bd3bbce8b8cfaf5f49bf891b3b2d1d0d Mon Sep 17 00:00:00 2001 From: Semyon1104 Date: Fri, 29 Nov 2024 15:36:40 +0300 Subject: [PATCH 14/14] f --- app/Graph/build.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/Graph/build.cpp b/app/Graph/build.cpp index e879503a..a799558f 100644 --- a/app/Graph/build.cpp +++ b/app/Graph/build.cpp @@ -38,7 +38,7 @@ void build_graph(Tensor& input, Tensor& output) { std::vector values_vector = *tensor.as(); std::vector> values_vector_2d( tensor.get_shape()[0], - std::vector(tensor.get_shape()[1], 0.0f)); + std::vector(tensor.get_shape()[1], 0.0F)); int q = 0; for (size_t i = 0; i < values_vector.size(); i++) { values_vector_2d[q][i - (q * tensor.get_shape()[1])] = values_vector[i]; @@ -48,7 +48,7 @@ void build_graph(Tensor& input, Tensor& output) { } std::vector> values_vector_2d_2( tensor.get_shape()[1], - std::vector(tensor.get_shape()[0], 0.0f)); + std::vector(tensor.get_shape()[0], 0.0F)); for (size_t i = 0; i < tensor.get_shape()[0]; ++i) { for (size_t j = 0; j < tensor.get_shape()[1]; ++j) {