#ifndef CORE_HPP #define CORE_HPP #include #include #include #include #include #include // Структура для описания слоя struct LayerStructure_t { int size; // Количество нейронов в слое std::vector sources; // Индексы слоев, которые являются входными для данного std::vector sourceBranches; // Ветка для каждого источника (-1 если не разделен, 0 или 1) int branch; // -1 если не разделен, 0 или 1 если слой работает с конкретной веткой bool isSplit; // true если слой разделяет выход на две ветки LayerStructure_t() : size(0), branch(-1), isSplit(false) {} LayerStructure_t(int s, const std::vector& src = {}) : size(s), sources(src), branch(-1), isSplit(false) { sourceBranches.resize(src.size(), -1); } }; // Параметры для передачи в шейдер через Push Constants struct TrainParams { uint32_t mode; // 0: FF, 1: OutError, 2: BackProp, 3: Update uint32_t prevSize; // Суммарный размер входов uint32_t nextSize; // Размер текущего слоя uint32_t wOff; // Смещение весов в буфере W uint32_t bOff; // Смещение смещений в буфере B uint32_t oOff; // Смещение входов в буфере O uint32_t nextOOff; // Смещение выходов в буфере O float lr; // Скорость обучения }; // Структура для обратной связи о процессе обучения struct TrainStatus { int epoch = 0; int totalEpochs = 0; int step = 0; int totalSteps = 0; double loss = 0.0; double totalLoss = 0.0; double lastEpochLoss = 0.0; double speed = 0.0; double eta = 0.0; float progress = 0.0f; long long params = 0; }; class NeuralNetwork { public: NeuralNetwork(LayerStructure_t layers[], int count, bool useVulkanParam); ~NeuralNetwork(); double train(const std::map>& inputs, const std::vector& target, double lr); std::vector feedForward(const std::map>& inputs); void syncToCPU(); void syncToGPU(); // Геттеры для UI const std::vector& getSizes() const { return sizes; } const std::vector>& getLayerSources() const { return layerSources; } const std::vector>& getSourceBranches() const { return layerSourceBranches; } const std::vector& getBranches() const { return branches; } const std::vector& getSplits() const { return splits; } private: bool useVulkan; int numLayers; // Метаданные архитектуры std::vector sizes; std::vector wOff; std::vector bOff; std::vector oOff; std::vector> layerSources; std::vector> layerSourceBranches; // Ветка для каждого источника std::vector branches; // Ветка каждого слоя (-1, 0, 1) std::vector splits; // Является ли слой split // Данные на стороне CPU std::vector h_weights; std::vector h_biases; std::vector h_outputs; std::vector h_errors; // Vulkan объекты vk::Instance instance; vk::PhysicalDevice physDev; vk::Device device; vk::Queue queue; vk::CommandPool cmdPool; vk::DescriptorSetLayout dsLayout; vk::DescriptorPool descriptorPool; vk::DescriptorSet descriptorSet; vk::PipelineLayout pipeLayout; vk::Pipeline pipeline; vk::ShaderModule shaderModule; vk::Buffer gpuW, gpuB, gpuO, gpuE, gpuT; vk::DeviceMemory memW, memB, memO, memE, memT; void *pW = nullptr, *pB = nullptr, *pO = nullptr, *pE = nullptr, *pT = nullptr; // Command buffer pooling std::vector cmdBuffers; uint32_t currentCmdBuffer = 0; void initVulkan(); void initVulkanResources(); uint32_t findMemoryType(uint32_t f, vk::MemoryPropertyFlags p); std::vector readFile(const std::string& filename); int calculateTotalInputSize(int layerIdx) const; }; #endif // CORE_HPP