Refactor project structure

This commit is contained in:
2026-03-28 19:56:39 +11:00
parent 1d267378b2
commit 8a2e721058
511 changed files with 59 additions and 48 deletions

View File

@@ -0,0 +1,960 @@
#include "ANSODTraininingEngine.h"
#include "Utility.h"
#include <random>
#include <cstdio>
#include <memory>
#include <regex>
namespace ANSCENTER
{
ANSODTRE::ANSODTRE() {
_projectDirectory = "C:\\ProgramData\\Sh7O7nUe7vJ";
_engineDirectory = "C:\\ProgramData\\mt5P9nTe5vG\\Engine\\CUDA11";
_modelTemplateDirectory = "C:\\ProgramData\\mt5P9nTe5vG\\Engine\\CUDA11";
_currentExperimentNumber = 1;
_isLicenseValid = false;
_licenseKey = "";
_zipPassword = "";
_changeProjectDirectory = false;
_isLatestEngine = false; // No use for this case
}
ANSODTRE::~ANSODTRE() {
_projects.clear();
_zipPassword = "";
_isLicenseValid = false;
_changeProjectDirectory = false;
_isLatestEngine = false;
}
void ANSODTRE::CheckLicense() {
try {
_isLicenseValid = ANSCENTER::ANSLicenseHelper::LicenseVerification(_licenseKey, 1002, "ODHUB-LV");//Default productId=1002 (ODHUB)
}
catch (std::exception& e) {
this->_logger.LogFatal("ANSODTRE::CheckLicense()", e.what(), __FILE__, __LINE__);
}
}
bool ANSODTRE::Init(std::string licenseKey,
std::string projectDirectory,
std::string engineDirectory,
std::string modelTemplateDirectory,
std::string modelZipPassword,
bool isLatestEngine)
{
_licenseKey = licenseKey;
_isLatestEngine = isLatestEngine;
CheckLicense();
if (!_isLicenseValid) {
this->_logger.LogError("ANSODTRE::Init", "Invalid license key", __FILE__, __LINE__);
return false;
}
if (projectDirectory.empty())_projectDirectory = "C:\\ProgramData\\Sh7O7nUe7vJ\\odhub";
else _projectDirectory = projectDirectory +"\\odhub";
_engineDirectory = engineDirectory;
_modelTemplateDirectory = modelTemplateDirectory;
if (_engineDirectory.empty())_engineDirectory = "C:\\ProgramData\\ANSCENTER\\Shared";
if (_modelTemplateDirectory.empty())_modelTemplateDirectory = "C:\\ProgramData\\ANSCENTER\\Shared";
// Change the project directory to 1 level down if there is 1 folder in the project directory
if(!FolderExist(_projectDirectory)) fs::create_directory(_projectDirectory);
_modelZipPassword = modelZipPassword;
_zipPassword = "Sh7O7nUe7vJ/417W0gWX+dSdfcP9hUqtf/fEqJGqxYL3PedvHubJag==";
_modelZipPassword = _zipPassword;
// Some logging in here
std::string _ansdnnEngine = _engineDirectory + "\\ansdn.exe";
if (!FileExist(_ansdnnEngine))this->_logger.LogError("ANSODTRE::Init", "ODHUB Engine is not installed. Please install ANS Runtime Engine", __FILE__, __LINE__);
std::string fastCfgTemplateFile = _modelTemplateDirectory + "\\FAST.cfg";
std::string accurateCfgTemplateFile = _modelTemplateDirectory + "\\ACCURATE.cfg";
std::string veryAccurateCfgTemplateFile = _modelTemplateDirectory + "\\VERYACCURATE.cfg";
std::string customCfgTemplateFile = _modelTemplateDirectory + "\\CUSTOM.cfg";
if (!FileExist(fastCfgTemplateFile))this->_logger.LogError("ANSODTRE::Init", "FAST.cfg template file is missing", __FILE__, __LINE__);
if (!FileExist(accurateCfgTemplateFile))this->_logger.LogError("ANSODTRE::Init", "ACCURATE.cfg template file is missing", __FILE__, __LINE__);
if (!FileExist(veryAccurateCfgTemplateFile))this->_logger.LogError("ANSODTRE::Init", "VERYACCURATE.cfg template file is missing", __FILE__, __LINE__);
if (!FileExist(customCfgTemplateFile))this->_logger.LogError("ANSODTRE::Init", "CUSTOM.cfg template file is missing", __FILE__, __LINE__);
std::string fastWeight = _modelTemplateDirectory + "\\FAST.weights";
std::string accurateWeight = _modelTemplateDirectory + "\\BASE.weights";
if (!FileExist(fastWeight))this->_logger.LogError("ANSODTRE::Init", "FAST model file is missing", __FILE__, __LINE__);
if (!FileExist(accurateWeight))this->_logger.LogError("ANSODTRE::Init", "ACCURATE model file is missing", __FILE__, __LINE__);
if (FolderExist(_projectDirectory) &&
FolderExist(_engineDirectory) &&
FolderExist(_modelTemplateDirectory))return true;
return false;
}
std::vector<std::string> ANSODTRE::GetProjects() {
_projects.clear();
std::vector<std::string> _projectNames;
for (auto& entry : std::filesystem::directory_iterator(_projectDirectory))
{
if (entry.is_directory())
{
_projects.push_back(entry.path().string());
_projectNames.push_back(ExtractFolderName(entry.path().string()));
}
}
return _projectNames;
}
std::vector<std::string> ANSODTRE::GetProjectExperiments(std::string projectName) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
std::string experimentPath = projectPath + "\\experiments";
if (FolderExist(experimentPath)) {
std::vector<std::string> files;
std::vector<std::string> experiments;
for (const auto& entry : std::filesystem::directory_iterator(experimentPath))
{
if (entry.is_regular_file() && entry.path().extension() == ".zip")
{
experiments.push_back(GetFileNameWithoutExtension(entry.path().string()));
}
}
return experiments;
}
else {
std::vector<std::string> experiments;
return experiments;
}
}
std::string ANSODTRE::GetProjectExperimentStatus(std::string projectName, int experimentNumber) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
std::string experimentFolder = projectPath + "\\experiments";
if (FolderExist(experimentFolder)) {
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber) + ".zip";
if (FileExist(experimentPath)) {
std::string evaluationPath = projectPath + "\\evaluations\\mAP_" + std::to_string(experimentNumber) + ".txt";
if (FileExist(evaluationPath)) return "EXPORTED";
else return "TRAINED";
}
else {
std::string configurationPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber) + "\\train.cfg";
if (FileExist(configurationPath))
{
std::string mapFile = projectPath + "\\experiments\\" + std::to_string(experimentNumber) + "\\mAP.txt";
if (FileExist(mapFile)) return "RUNNING";
else return "CONFIGURED";
}
else {
return "UPLOADED";
}
}
}
else {
std::string dataPath = projectPath + "\\data";
if (FileExist(dataPath))
{
return "CREATED";
}
else {
return "UPLOADED";
}
}
}
else return "NOTFOUND";
}
bool ANSODTRE::CreateProject(std::string projectName) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (projectPath.empty()) {
std::string newProjectPath = _projectDirectory + "\\" + _projectName;
if (FolderExist(newProjectPath))return false;
fs::create_directory(newProjectPath);
_projects.push_back(newProjectPath);
return true;
}
return false;
}
bool ANSODTRE::DeleteProject(std::string projectName) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
return DeleteFolder(projectPath);
}
return false;
}
bool ANSODTRE::SetWorkingDirectory(std::string workingDirectory) {
if (FolderExist(workingDirectory)) {
size_t lastSlashPos = workingDirectory.find_last_of("\\/");
if (lastSlashPos != std::string::npos && workingDirectory.substr(lastSlashPos + 1) == "data") {
workingDirectory = workingDirectory.substr(0, lastSlashPos);
}
_workingDirectory = workingDirectory;
std::string dataPath = _workingDirectory + "\\data";
std::string pbLabelPath = dataPath + "\\label_map.pbtxt";
if (FileExist(pbLabelPath)) return true;
else false;
}
return false;
}
bool ANSODTRE::UploadTrainingData(std::string projectName) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
std::string dataPath = projectPath + "\\data";
if (FolderExist(dataPath))DeleteFolder(dataPath);
fs::create_directory(dataPath);
std::string sourceDataPath = _workingDirectory + "\\data";
bool useANSClassFile = true;
std::string sourceLabelPath = sourceDataPath + "\\ANS_Class.json";
if (!FileExist(sourceLabelPath)) {
sourceLabelPath = sourceDataPath + "\\label_map.pbtxt";
useANSClassFile = false;
}
if (!FileExist(sourceLabelPath)) return false;
std::string classesName = dataPath + "\\classes.names";
if (FileExist(classesName))DeleteFile(classesName);
int numberOfClass = GenerateClassNamesFile(sourceLabelPath, classesName, useANSClassFile);
if (numberOfClass <= 0) return false;
GenerateTrainDataSet(sourceDataPath, dataPath + "\\train", dataPath + "\\test", 0.8);
std::string objectDataFile = dataPath + "\\object.data";
GenerateObjectDataFile(numberOfClass, objectDataFile);
return FileExist(objectDataFile);
}
bool ANSODTRE::CreateTrainingEngine(std::string projectName,
int experimentNumber,
int extractorType,
long numberStep,
int batchSize,
double learningRate)// extractorType =0: FAST, 1: ACCURATE; 2: VERY ACCURATE
{
_projectName = Space2Underscore(projectName);
const int _extractorType = extractorType;
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber);
std::string experimentParentFolder = GetParentFolder(experimentPath);
if (!FolderExist(experimentParentFolder))fs::create_directory(experimentParentFolder);
//0. Check if the experiement folder exist
std::string zipExperimentPath = experimentPath + ".zip";
if (FileExist(zipExperimentPath)) { // If the experiment folder is already zipped, we need to unzip it
bool unzipResult = ExtractProtectedZipFile(zipExperimentPath, _zipPassword, std::to_string(experimentNumber), experimentPath);
if (!unzipResult) {
unzipResult=ExtractProtectedZipFile(zipExperimentPath, _modelZipPassword, std::to_string(experimentNumber), experimentPath);
}
if (unzipResult) {
DeleteFile(zipExperimentPath);
}
DeleteWeightsFiles(experimentPath);
}
//1. Create a brand new experiment folder
if (!FolderExist(experimentPath))fs::create_directory(experimentPath);
std::string trainCfgFile = experimentPath + "\\train.cfg";
std::string testCfgFile = experimentPath + "\\test.cfg";
std::string classesName = projectPath + "\\data\\classes.names";
std::string objectDataFile = projectPath + "\\data\\object.data";
//2. Delete the old configuration files
if (FileExist(trainCfgFile))DeleteFile(trainCfgFile);
if (FileExist(testCfgFile))DeleteFile(testCfgFile);
//3. Copy classes.names to the experiment folder
std::string experimentClassesName = experimentPath + "\\classes.names";
if (FileExist(experimentClassesName)) DeleteFile(experimentClassesName);
CopyFile(classesName, experimentClassesName);
//4. Copy object.data to the experiment folder
std::string experimentObjectDataFile = experimentPath + "\\object.data";
if (FileExist(experimentObjectDataFile)) DeleteFile(experimentObjectDataFile);
CopyFile(objectDataFile, experimentObjectDataFile);
int numberOfClass = ReadClassesValue(experimentObjectDataFile);
int step1 = static_cast<int>(numberStep * 0.8);
int step2 = static_cast<int>(numberStep * 0.9);
int subDivision = 64; // Hardcoded
int filters = (numberOfClass + 5) * 3;
//2. Create a training configuration file
std::map<std::string, std::string> trainReplacements = {
{"BATCH", std::to_string(batchSize)},
{"SUBDIVISION", "64"},
{"LEARNING_RATE", std::to_string(learningRate)},
{"MAX_BATCHES", std::to_string(numberStep)},
{"STEP1", std::to_string(step1)},
{"STEP2", std::to_string(step2)},
{"FILTERS", std::to_string(filters)},
{"CLASSES", std::to_string(numberOfClass)}};
std::map<std::string, std::string> testReplacements = {
{"BATCH", "1"},
{"SUBDIVISION", "1"},
{"LEARNING_RATE", std::to_string(learningRate)},
{"MAX_BATCHES", std::to_string(numberStep)},
{"STEP1", std::to_string(step1)},
{"STEP2", std::to_string(step2)},
{"FILTERS", std::to_string(filters)},
{"CLASSES", std::to_string(numberOfClass)}};
std::string trainCfgTemplateFile;;
if (_extractorType == 0) {
trainCfgTemplateFile = _modelTemplateDirectory + "\\FAST.cfg";
}
else if (_extractorType == 1) {
trainCfgTemplateFile = _modelTemplateDirectory + "\\ACCURATE.cfg";
}
else if (_extractorType == 2) {
trainCfgTemplateFile = _modelTemplateDirectory + "\\VERYACCURATE.cfg";
}
else if (_extractorType == 3) {
trainCfgTemplateFile = _modelTemplateDirectory + "\\CUSTOM.cfg";
}
else {
trainCfgTemplateFile = _modelTemplateDirectory + "\\CUSTOM.cfg";
}
std::cout<< "trainCfgTemplateFile: " << trainCfgTemplateFile << std::endl;
GenerateConfigFile(trainCfgTemplateFile, trainCfgFile, trainReplacements);
GenerateConfigFile(trainCfgTemplateFile, testCfgFile, testReplacements);
if (!FileExist(trainCfgFile)) this->_logger.LogError("ANSODTRE::CreateTrainingEngine", "Missing train.cfg file", __FILE__, __LINE__);
if (!FileExist(testCfgFile)) this->_logger.LogError("ANSODTRE::CreateTrainingEngine", "Missing test.cfg file", __FILE__, __LINE__);
if (!FileExist(experimentClassesName)) this->_logger.LogError("ANSODTRE::CreateTrainingEngine", "MMissing classes.names file", __FILE__, __LINE__);
if (!FileExist(experimentObjectDataFile)) this->_logger.LogError("ANSODTRE::CreateTrainingEngine", "Missing object.data file", __FILE__, __LINE__);
if ((FileExist(trainCfgFile)) &&
(FileExist(testCfgFile)) &&
(FileExist(experimentClassesName)) &&
(FileExist(experimentObjectDataFile)))return true;
return false;
}
std::string ANSODTRE::GenerateTrainingCommand(std::string projectName,int experimentNumber, int extractorType) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber);
std::string trainScript = _engineDirectory + "\\ansdn.exe";
std::string experimentObjectDataFile = experimentPath + "\\object.data";
std::string trainCfgFile = experimentPath + "\\train.cfg";
std::string preTrainWeightFile = _modelTemplateDirectory + "\\FAST.weights";
if (extractorType > 0)preTrainWeightFile = _modelTemplateDirectory + "\\BASE.weights";
// Override the preTrainWeightFile if the experiment folder is already zipped
std::string zipExperimentPath = experimentPath + ".zip";
std::string experimentParentFolder = GetParentFolder(experimentPath);
if (FileExist(zipExperimentPath)) { // If the experiment folder is already zipped, we need to unzip it
bool unzipResult = ExtractProtectedZipFile(zipExperimentPath, _zipPassword, std::to_string(experimentNumber), experimentPath);
if (!unzipResult) {
unzipResult = ExtractProtectedZipFile(zipExperimentPath, _modelZipPassword, std::to_string(experimentNumber), experimentPath);
}
if (unzipResult) {
DeleteFile(zipExperimentPath);
}
}
std::string lastTrainWeightFile = experimentPath + "\\train_last.weights";
if(FileExist(lastTrainWeightFile))preTrainWeightFile = experimentPath + "\\train_last.weights";
if (!FileExist(trainScript)) this->_logger.LogError("ANSODTRE::GenerateTrainingCommand", "ANSODTRE Engine is not installed", __FILE__, __LINE__);
if (!FileExist(trainCfgFile)) this->_logger.LogError("ANSODTRE::GenerateTrainingCommand", "Missing train.cfg file", __FILE__, __LINE__);
if (!FileExist(preTrainWeightFile)) this->_logger.LogError("ANSODTRE::GenerateTrainingCommand", "Missing pre-trained weight file", __FILE__, __LINE__);
if (!FileExist(experimentObjectDataFile)) this->_logger.LogError("ANSODTRE::GenerateTrainingCommand", "Missing object.data file", __FILE__, __LINE__);
if ((FileExist(trainScript)) &&
(FileExist(trainCfgFile)) &&
(FileExist(preTrainWeightFile)) &&
(FileExist(experimentObjectDataFile))) {
std::string trainCommand = trainScript + " detector train " + "\""+
experimentObjectDataFile + "\""+ " " + +"\"" +
trainCfgFile + +"\"" + " " + "\"" +
preTrainWeightFile + "\"" +
" -dont_show " + " -map";
return trainCommand;
}
this->_logger.LogError("ANSODTRE::GenerateTrainingCommand", "Missing configuration files", __FILE__, __LINE__);
return "";
}
else {
this->_logger.LogError("ANSODTRE::GenerateTrainingCommand", "project path is not exist", __FILE__, __LINE__);
return "";
}
}
std::string ANSODTRE::GenerateCustomTrainingCommand(std::string projectName, int experimentNumber, int extractorType, std::string pretrainedModel) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber);
std::string trainScript = _engineDirectory + "\\ansdn.exe";
std::string experimentObjectDataFile = experimentPath + "\\object.data";
std::string trainCfgFile = experimentPath + "\\train.cfg";
std::string preTrainWeightFile = pretrainedModel;
if (!FileExist(preTrainWeightFile)) {
preTrainWeightFile = _modelTemplateDirectory + "\\FAST.weights";
if (extractorType > 0)preTrainWeightFile = _modelTemplateDirectory + "\\BASE.weights";
}
// Override the preTrainWeightFile if the experiment folder is already zipped
std::string zipExperimentPath = experimentPath + ".zip";
std::string experimentParentFolder = GetParentFolder(experimentPath);
if (FileExist(zipExperimentPath)) { // If the experiment folder is already zipped, we need to unzip it
bool unzipResult = ExtractProtectedZipFile(zipExperimentPath, _zipPassword, std::to_string(experimentNumber), experimentPath);
if (!unzipResult) {
unzipResult = ExtractProtectedZipFile(zipExperimentPath, _modelZipPassword, std::to_string(experimentNumber), experimentPath);
}
if (unzipResult) {
DeleteFile(zipExperimentPath);
}
}
std::string lastTrainWeightFile = experimentPath + "\\train_last.weights";
if (FileExist(lastTrainWeightFile))preTrainWeightFile = experimentPath + "\\train_last.weights";
if (!FileExist(trainScript)) this->_logger.LogError("ANSODTRE::GenerateCustomTrainingCommand", "ANSODTRE Engine is not installed", __FILE__, __LINE__);
if (!FileExist(trainCfgFile)) this->_logger.LogError("ANSODTRE::GenerateCustomTrainingCommand", "Missing train.cfg file", __FILE__, __LINE__);
if (!FileExist(preTrainWeightFile)) this->_logger.LogError("ANSODTRE::GenerateCustomTrainingCommand", "Missing pre-trained weight file", __FILE__, __LINE__);
if (!FileExist(experimentObjectDataFile)) this->_logger.LogError("ANSODTRE::GenerateCustomTrainingCommand", "Missing object.data file", __FILE__, __LINE__);
if ((FileExist(trainScript)) &&
(FileExist(trainCfgFile)) &&
(FileExist(preTrainWeightFile)) &&
(FileExist(experimentObjectDataFile))) {
std::string trainCommand = trainScript + " detector train " + "\"" +
experimentObjectDataFile + "\"" + " " + +"\"" +
trainCfgFile + +"\"" + " " + "\"" +
preTrainWeightFile + "\"" +
" -dont_show " + " -map";
return trainCommand;
}
this->_logger.LogError("ANSODTRE::GenerateCustomTrainingCommand", "Missing configuration files", __FILE__, __LINE__);
return "";
}
else {
this->_logger.LogError("ANSODTRE::GenerateCustomTrainingCommand", "project path is not exist", __FILE__, __LINE__);
return "";
}
}
std::string ANSODTRE::GenerateEvaluateModelCommand(std::string projectName, int experimentNumber, bool &zipModelExist) {
_projectName = Space2Underscore(projectName);
zipModelExist = false;
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber);
std::string trainScript = _engineDirectory + "\\ansdn.exe";
std::string experimentObjectDataFile = experimentPath + "\\object.data";
std::string testCfgFile = experimentPath + "\\test.cfg";
std::string preTrainWeightFile = experimentPath + "\\train_last.weights";
// Override the preTrainWeightFile if the experiment folder is already zipped
std::string zipExperimentPath = experimentPath + ".zip";
std::string experimentParentFolder = GetParentFolder(experimentPath);
if (FileExist(zipExperimentPath)) { // If the experiment folder is already zipped, we need to unzip it
bool unzipResult = ExtractProtectedZipFile(zipExperimentPath, _zipPassword, std::to_string(experimentNumber), experimentPath);
if (!unzipResult) {
unzipResult = ExtractProtectedZipFile(zipExperimentPath, _modelZipPassword, std::to_string(experimentNumber), experimentPath);
}
if (unzipResult) {
zipModelExist = true;
}
}
if (!FileExist(trainScript)) this->_logger.LogError("ANSODTRE::GenerateEvaluateModelCommand", "ANSODTRE Engine is not installed", __FILE__, __LINE__);
if (!FileExist(testCfgFile)) this->_logger.LogError("ANSODTRE::GenerateEvaluateModelCommand", "Missing train.cfg file", __FILE__, __LINE__);
if (!FileExist(preTrainWeightFile)) this->_logger.LogError("ANSODTRE::GenerateEvaluateModelCommand", "Missing pre-trained weight file", __FILE__, __LINE__);
if (!FileExist(experimentObjectDataFile)) this->_logger.LogError("ANSODTRE::GenerateEvaluateModelCommand", "Missing object.data file", __FILE__, __LINE__);
if ((FileExist(trainScript)) &&
(FileExist(testCfgFile)) &&
(FileExist(preTrainWeightFile)) &&
(FileExist(experimentObjectDataFile))) {
std::string evaluateCommand = trainScript + " detector map " + "\"" +
experimentObjectDataFile + "\"" + " " + "\"" +
testCfgFile + "\"" + " " + "\"" +
preTrainWeightFile + "\"" +
" -dont_show " + " -map";
return evaluateCommand;
}
this->_logger.LogError("ANSODTRE::GenerateEvaluateModelCommand", "Missing configuration files", __FILE__, __LINE__);
return "";
}
else {
this->_logger.LogError("ANSODTRE::GenerateEvaluateModelCommand", "project path is not exist", __FILE__, __LINE__);
return "";
}
}
std::string ANSODTRE::GenerateTestCommand(std::string projectName, int experimentNumber, bool& zipModelExist, const std::string& testDataFolder) {
_projectName = Space2Underscore(projectName);
zipModelExist = false;
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber);
std::string trainScript = _engineDirectory + "\\ansdn.exe";
std::string experimentObjectDataFile = experimentPath + "\\object.data";
std::string testCfgFile = experimentPath + "\\test.cfg";
std::string testClassesName = experimentPath + "\\classes.names";
std::string preTrainWeightFile = experimentPath + "\\train_last.weights";
// Override the preTrainWeightFile if the experiment folder is already zipped
std::string zipExperimentPath = experimentPath + ".zip";
std::string experimentParentFolder = GetParentFolder(experimentPath);
if (FileExist(zipExperimentPath)) { // If the experiment folder is already zipped, we need to unzip it
bool unzipResult = ExtractProtectedZipFile(zipExperimentPath, _zipPassword, std::to_string(experimentNumber), experimentPath);
if (!unzipResult) {
unzipResult = ExtractProtectedZipFile(zipExperimentPath, _modelZipPassword, std::to_string(experimentNumber), experimentPath);
}
if (unzipResult) {
zipModelExist = true;
}
}
if (!FileExist(trainScript)) this->_logger.LogError("ANSODTRE::GenerateTestCommand", "ANSODTRE Engine is not installed", __FILE__, __LINE__);
if (!FileExist(testCfgFile)) this->_logger.LogError("ANSODTRE::GenerateTestCommand", "Missing train.cfg file", __FILE__, __LINE__);
if (!FileExist(preTrainWeightFile)) this->_logger.LogError("ANSODTRE::GenerateTestCommand", "Missing pre-trained weight file", __FILE__, __LINE__);
if (!FileExist(experimentObjectDataFile)) this->_logger.LogError("ANSODTRE::GenerateTestCommand", "Missing object.data file", __FILE__, __LINE__);
// Create test folder.
// testDataFolder
// - data: image files
// - test.cfg
// - classes.names
// - object.data
// - test.txt
// Assuming that the data folder is already created and contains the image files
std::string testFolder_ClassesNames = testDataFolder + "\\classes.names";
std::string testFolder_ObjectData = testDataFolder + "\\object.data";
std::string testFolder_TestTxt = testDataFolder + "\\test.txt";
// Copy the classes.names file to testFolder_ClassesNames
if (FileExist(testFolder_ClassesNames))DeleteFile(testFolder_ClassesNames);
CopyFile(testClassesName, testFolder_ClassesNames);
// List all the image files in the data folder and write to test.txt
if (FileExist(testFolder_TestTxt))DeleteFile(testFolder_TestTxt);
std::ofstream testTxtFile(testFolder_TestTxt);
if (testTxtFile.is_open()) {
for (const auto& entry : std::filesystem::directory_iterator(testDataFolder)) {
if ((entry.is_regular_file() && entry.path().extension() == ".jpg")||
(entry.is_regular_file() && entry.path().extension() == ".jpeg")||
(entry.is_regular_file() && entry.path().extension() == ".png")||
(entry.is_regular_file() && entry.path().extension() == ".bmp"))
{
testTxtFile << entry.path().string() << std::endl;
}
}
testTxtFile.close();
}
else {
this->_logger.LogError("ANSODTRE::GenerateTestCommand", "Cannot open test.txt file to write image paths", __FILE__, __LINE__);
return "";
}
// Create the object.data file in the test folder with follow contents
//classes = 4 (read from classes.names file)
//test = testTxtFile path
int classCount = 0;
std::ifstream classesFile(testFolder_ClassesNames);
if (classesFile.is_open()) {
std::string line;
while (std::getline(classesFile, line)) {
classCount++;
}
classesFile.close();
}
else {
this->_logger.LogError("ANSODTRE::GenerateTestCommand", "Cannot open classes.names file to read class count", __FILE__, __LINE__);
return "";
}
std::ofstream testObjectFile(testFolder_ObjectData);
if (testObjectFile.is_open()) {
testObjectFile << "classes = " << classCount << std::endl;
testObjectFile << "test = " << testFolder_TestTxt << std::endl;
testObjectFile.close();
}
else {
this->_logger.LogError("ANSODTRE::GenerateTestCommand", "Cannot open object.data file to write image paths", __FILE__, __LINE__);
return "";
}
if ((FileExist(trainScript)) &&
(FileExist(testCfgFile)) &&
(FileExist(preTrainWeightFile)) &&
(FileExist(experimentObjectDataFile))) {
std::string evaluateCommand = trainScript + " detector map " + "\"" +
testFolder_ObjectData + "\"" + " " + "\"" +
testCfgFile + "\"" + " " + "\"" +
preTrainWeightFile + "\"" +
" -dont_show " + " -map";
return evaluateCommand;
}
this->_logger.LogError("ANSODTRE::GenerateTestCommand", "Missing configuration files", __FILE__, __LINE__);
return "";
}
else {
this->_logger.LogError("ANSODTRE::GenerateTestCommand", "project path is not exist", __FILE__, __LINE__);
return "";
}
}
bool ANSODTRE::DownloadModel(std::string projectName, int experimentNumber, std::string destZipDirectory, int modelModel) {
_projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
//0. Get all files in the experiment folder
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber);
std::string zipExperimentPath = experimentPath + ".zip";
std::string experimentParentFolder = GetParentFolder(experimentPath);
if (FileExist(zipExperimentPath)) { // If the experiment folder is already zipped, we need to unzip it
if (ExtractProtectedZipFile(zipExperimentPath, _zipPassword, std::to_string(experimentNumber), experimentPath))
{
DeleteFile(zipExperimentPath);
}
else {
this->_logger.LogError("ANSODTRE::DownloadModel", "Can not unzip model zip file to extract information. Invalid password.", __FILE__, __LINE__);
return false;
}
}
//1. Remove previuos weights files
DeleteWeightsFiles(experimentPath);
// 2. Get the names of classes.names
std::string classesNameFile = experimentPath + "\\classes.names";
std::ifstream inFile(classesNameFile);
if (!inFile.is_open()) {
this->_logger.LogError("ANSODTRE::DownloadModel", "cannot open file to save model information.", __FILE__, __LINE__);
return false;
}
std::vector<std::string> classesNames;
std::string line;
while (std::getline(inFile, line)) {
classesNames.push_back(line);
}
inFile.close();
// 3. Create Categories folder
std::string categoriesFolder = experimentPath + "\\Categories";
if (FolderExist(categoriesFolder))DeleteFolder(categoriesFolder);
fs::create_directory(categoriesFolder);
for (size_t i = 0; i < classesNames.size(); ++i) {
std::ofstream outFile(categoriesFolder + "/" + classesNames[i] + "." + std::to_string(i+1));
outFile.close();
}
//4. Create a text file name yolo.txt
std::string yoloTxtFile = experimentPath + "\\yolo.txt";
std::ofstream outFile(yoloTxtFile);
outFile.close();
//5. Zip the experiment folder
std::string zipFile = experimentParentFolder + "\\" + std::to_string(experimentNumber) + ".zip";
if (ZipFolderWithPassword(experimentPath.c_str(), zipFile.c_str(), _zipPassword.c_str())) {
DeleteFolder(experimentPath);
std::string destZipFilePath = destZipDirectory + "\\" + projectName + "_" + std::to_string(experimentNumber) + ".zip";
CopyFile(zipFile, destZipFilePath);
if (FileExist(destZipFilePath))return true;
return false;
}
this->_logger.LogError("ANSODTRE::DownloadModel", "Can not unzip model zip file to extract information. Invalid password.", __FILE__, __LINE__);
return false;
}
else {
this->_logger.LogError("ANSODTRE::DownloadModel", "Invalid project path.", __FILE__, __LINE__);
return false;
}
}
std::string ANSODTRE::EvaluateModel(std::string projectName, int experimentNumber) {
bool zipModelExist = false;
std::string _projectName = Space2Underscore(projectName);
std::string projectPath = FindFilePathInFileList(_projects, _projectName);
if (FolderExist(projectPath)) {
std::string experimentPath = projectPath + "\\experiments\\" + std::to_string(experimentNumber);
std::string zipExperimentPath = experimentPath + ".zip";
std::string evaluateCommand = GenerateEvaluateModelCommand(_projectName, experimentNumber, zipModelExist);
if (evaluateCommand.empty()) {
this->_logger.LogError("ANSODTRE::EvaluateModel", "Invalid command to evaluate model", __FILE__, __LINE__);
return "";
}
std::string result = ExecuteCommand(evaluateCommand.c_str());
if (result.empty()) {
this->_logger.LogError("ANSODTRE::EvaluateModel", "Failed to evaluate model", __FILE__, __LINE__);
return "";
}
//Remove previuos weights files
DeleteWeightsFiles(experimentPath);
if (FileExist(zipExperimentPath))DeleteFile(zipExperimentPath);
//Zip the experiment folder
if (ZipFolderWithPassword(experimentPath.c_str(), zipExperimentPath.c_str(), _zipPassword.c_str())) {
DeleteFolder(experimentPath);
}
return ParseMAP(result);
}
else {
this->_logger.LogError("ANSODTRE::EvaluateModel", "Invalid project path.", __FILE__, __LINE__);
return "";
}
}
std::string ANSODTRE::ParseTrainingResults(std::string trainingResults) {
return trainingResults;
}
bool ANSODTRE::CheckEngineStatus() {
const char* targetProcess = "ansdn.exe"; // Replace with the target process name
if (IsProcessRunning(targetProcess)) {
return true;
}
else {
return false;
}
}
bool ANSODTRE::CheckEngine() {
std::string inferenceCommand = "C:\\ProgramData\\ANSCENTER\\Shared\\ansdn.exe detector";
std::string result = ExecuteCommand(inferenceCommand.c_str());
if (result.empty()) {
return false;
}
else {
std::string target = "ODHUB_TRAIN_COMPLETE";
// Check if the target text is found in the input text
if (result.find(target) != std::string::npos) {
std::cout << "Engine is installed correctly." << std::endl;
return true; // Text is found
}
else {
std::cout << "Engine is not installed correctly." << std::endl;
return false; // Text is not found
}
}
}
//Private functions
std::string ANSODTRE::ParseMAP(const std::string& text) {
std::regex mapPattern("mean average precision \\(mAP@0\\.50\\) = ([0-9\\.]+)");
std::smatch matches;
if (std::regex_search(text, matches, mapPattern) && matches.size() > 1) {
return matches[1].str();
}
else {
return "0.00";
}
}
std::string ANSODTRE::AdjustRootDirectory(const std::string& root) {
std::filesystem::path rootPath(root);
std::vector<std::filesystem::path> subdirectories;
for (const auto& entry : std::filesystem::directory_iterator(rootPath)) {
if (entry.is_directory()) {
subdirectories.push_back(entry.path());
}
}
if (subdirectories.size() == 1) {
return subdirectories[0].string();
}
else {
return root;
}
}
int ANSODTRE::GenerateClassNamesFile(std::string labelMapFile, std::string objectDataFile, bool useANSClassFile) {
if (!FileExist(labelMapFile)) return 0;
if (useANSClassFile) {
// Use the ANS Class file
std::vector<std::string> classVec = ParseANSClass(labelMapFile);
if (classVec.empty()) return 0;
std::ofstream outFile(objectDataFile);
std::string line;
int fileLine = 0;
for (auto& item : classVec) {
outFile << item << "\n";
fileLine++;
}
outFile.close();
return fileLine;
}
else {
std::ifstream inFile(labelMapFile);
std::ofstream outFile(objectDataFile);
if (!inFile.is_open() || !outFile.is_open()) {
return 0;
}
std::string line;
// Updated pattern: allows optional spaces between name and the colon
std::regex namePattern(R"(name\s*:\s*'(.*)')");
int fileLine = 0;
while (std::getline(inFile, line)) {
std::smatch matches;
std::cout << line << std::endl;
if (std::regex_search(line, matches, namePattern) && matches.size() > 1) {
outFile << matches[1].str() << "\n";
fileLine++;
}
}
inFile.close();
outFile.close();
return fileLine;
}
}
bool ANSODTRE::GenerateObjectDataFile(int numberOfClass, std::string objectDataFile) {
std::string projectName = GetParentFolder(objectDataFile);
if (FileExist(objectDataFile))DeleteFile(objectDataFile);
std::string classesName = projectName + "\\classes.names";
std::string trainTxt = projectName + "\\train.txt";
std::string testTxt = projectName + "\\test.txt";
if ((FileExist(classesName)) &&
(FileExist(trainTxt)) &&
(FileExist(testTxt)))
{
std::ofstream outFile(objectDataFile);
outFile << "classes = " << numberOfClass << "\n";
outFile << "train = " << trainTxt << "\n";
outFile << "valid = " << testTxt << "\n";
outFile << "names = " << classesName << "\n";
outFile.close();
return true;
}
return false;
}
void ANSODTRE::GenerateTrainDataSet(const std::string& sourceFolder, const std::string& trainFolder, const std::string& testFolder, double trainRatio) {
if (FolderExist(trainFolder))DeleteFolder(trainFolder);
if (FolderExist(testFolder))DeleteFolder(testFolder);
fs::create_directory(trainFolder);
fs::create_directory(testFolder);
std::unordered_map<std::string, std::vector<std::filesystem::path>> fileGroups;
for (const auto& entry : std::filesystem::directory_iterator(sourceFolder)) {
std::string extension = entry.path().extension().string();
boost::algorithm::to_lower(extension);
if (entry.is_regular_file()) {
if (extension == ".jpg" ||
extension == ".jpeg" ||
extension == ".png" ||
extension == ".bmp") fileGroups[entry.path().stem().string()].push_back(entry.path());
}
}
std::vector<std::string> groupNames;
for (const auto& group : fileGroups) {
groupNames.push_back(group.first);
}
std::ofstream trainFile(std::filesystem::path(trainFolder).parent_path() / "train.txt");
std::ofstream testFile(std::filesystem::path(testFolder).parent_path() / "test.txt");
size_t trainSize = static_cast<size_t>(groupNames.size() * trainRatio);
for (size_t i = 0; i < groupNames.size(); ++i) {
const auto& groupName = groupNames[i];
const auto& files = fileGroups[groupName];
for (const auto& file : files) {
std::string txtSourceFile = sourceFolder + "\\" + GetFileNameWithoutExtension(file.filename().string()) + ".txt";
if (i < trainSize) {
std::string txtTrainFile = trainFolder + "\\" + GetFileNameWithoutExtension(file.filename().string()) + ".txt";
std::string fileName = file.filename().string();
std::string fileExtension = GetFileExtension(fileName);
if (fileExtension == ".txt" ||
fileExtension == ".jpeg" ||
fileExtension == ".jpg" ||
fileExtension == ".png" ||
fileExtension == ".bmp")
{
if (FileExist(txtSourceFile)) {
std::filesystem::copy(file, trainFolder / file.filename());
CopyFile(txtSourceFile, txtTrainFile);
trainFile << (trainFolder / file.filename()).string() << "\n";
}
}
}
else {
std::string fileName = file.filename().string();
std::string fileExtension = GetFileExtension(fileName);
if (fileExtension == ".txt" ||
fileExtension == ".jpeg" ||
fileExtension == ".jpg" ||
fileExtension == ".png" ||
fileExtension == ".bmp")
{
if (FileExist(txtSourceFile)) {
std::string txtTestFile = testFolder + "\\" + GetFileNameWithoutExtension(file.filename().string()) + ".txt";
std::filesystem::copy(file, testFolder / file.filename());
CopyFile(txtSourceFile, txtTestFile);
testFile << (testFolder / file.filename()).string() << "\n";
}
}
}
}
}
trainFile.close();
testFile.close();
}
bool ANSODTRE::GenerateConfigFile(const std::string& templateFile,
const std::string& outputFile,
const std::map<std::string,std::string>& replacements) {
std::ifstream inFile(templateFile);
std::ofstream outFile(outputFile);
if (!inFile.is_open() || !outFile.is_open()) {
return false;
}
std::string line;
while (std::getline(inFile, line)) {
for (const auto& replacement : replacements) {
size_t pos = line.find("$" + replacement.first);
while (pos != std::string::npos) {
line.replace(pos, replacement.first.size() + 1, replacement.second);
pos = line.find("$" + replacement.first, pos + replacement.second.size());
}
}
outFile << line << "\n";
}
inFile.close();
outFile.close();
return FileExist(outputFile);
}
int ANSODTRE::ReadClassesValue(const std::string& filePath) {
std::ifstream inFile(filePath);
if (!inFile.is_open()) {
return 0;
}
std::ofstream outFile(filePath, std::ios_base::app);
if (!outFile.is_open()) {
return 0;
}
std::string currentFolderName = GetParentFolder(filePath);
outFile << "backup = " << currentFolderName << "\n";
outFile.close();
std::string line;
while (std::getline(inFile, line)) {
if (line.find("classes") == 0) {
size_t pos = line.find("=");
if (pos != std::string::npos) {
std::string classesValue = line.substr(pos + 1);
inFile.close();
return std::stoi(classesValue);
}
}
}
inFile.close();
return 0;
}
void ANSODTRE::DeleteWeightsFiles(const std::string& folderPath) {
for (const auto& entry : std::filesystem::directory_iterator(folderPath)) {
if (entry.is_regular_file() && entry.path().extension() == ".weights" && entry.path().filename() != "train_last.weights") {
std::filesystem::remove(entry.path());
}
}
}
}

View File

@@ -0,0 +1,46 @@
#ifndef ANSODTRE_H
#define ANSODTRE_H
#pragma once
#include "ANSTrainingEngine.h"
namespace ANSCENTER {
class ANSTRE_API ANSODTRE: public ANSTRE {
public:
ANSODTRE();
~ANSODTRE();
[[nodiscard]] bool Init(std::string licenseKey, std::string projectDirectory, std::string engineDirectory, std::string modelTemplateDirectory, std::string modelZipPassword, bool isLatestEngine)override;
[[nodiscard]] std::vector<std::string> GetProjects()override;// Return a list of projects in the project directory
[[nodiscard]] std::vector<std::string> GetProjectExperiments(std::string projectName)override;// Return a list of experiments for a specific project
[[nodiscard]] bool CreateProject(std::string projectName)override;
[[nodiscard]] bool DeleteProject(std::string projectName)override;
[[nodiscard]] bool SetWorkingDirectory(std::string workingDirectory)override;
[[nodiscard]] bool UploadTrainingData(std::string projectName)override; // Upload the training data to the project
[[nodiscard]] bool CreateTrainingEngine(std::string projectName,int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate)override;// extractorType =0: FAST, 1: ACCURATE; 2: VERY ACCURATE
[[nodiscard]] std::string GetProjectExperimentStatus(std::string projectName, int experimentNumber)override;// Return the status of a specific experiment
[[nodiscard]] std::string GenerateTrainingCommand(std::string projectName,int experimentNumber, int extractorType)override; //Generate the training command
[[nodiscard]] std::string GenerateCustomTrainingCommand(std::string projectName, int experimentNumber, int extractorType, std::string pretrainedModel)override; //Generate the training command
[[nodiscard]] std::string GenerateEvaluateModelCommand(std::string projectName,int experimentNumber, bool& zipModelExist)override; //Evaluate the accuracy of the model
[[nodiscard]] std::string EvaluateModel(std::string projectName, int experimentNumber)override; //Evaluate the accuracy of the model
[[nodiscard]] bool DownloadModel(std::string projectName, int experimentNumber, std::string destZipDirectory, int modelModel = 0)override;
[[nodiscard]] std::string ParseTrainingResults(std::string trainingResults)override;
[[nodiscard]] bool CheckEngineStatus() override;
[[nodiscard]] bool CheckEngine() override;
[[nodiscard]] std::string GenerateTestCommand(std::string projectName, int experimentNumber, bool& zipModelExist, const std::string& testDataFolder)override; //Generate the test command
private:
std::string AdjustRootDirectory(const std::string& root);
int GenerateClassNamesFile(std::string labelMapFile, std::string objectDataFile, bool useANSClassFile);
bool GenerateObjectDataFile(int numberOfClass, std::string objectDataFile);
void GenerateTrainDataSet(const std::string& sourceFolder, const std::string& trainFolder, const std::string& testFolder, double trainRatio = 0.8);
bool GenerateConfigFile(const std::string& templateFile,
const std::string& outputFile,
const std::map<std::string, std::string>& replacements);
int ReadClassesValue(const std::string& filePath);
std::string ParseMAP(const std::string& text);
void CheckLicense();
void DeleteWeightsFiles(const std::string& folderPath);
};
}
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,118 @@
#ifndef ANSTRE_H
#define ANSTRE_H
#define ANSTRE_API __declspec(dllexport)
#pragma once
#include <cstdint>
#include <iostream>
#include <vector>
#include "LabVIEWHeader/extcode.h"
#include "ANSLicense.h"
#include <map>
namespace ANSCENTER {
class ANSTRE_API ANSTRE {
public:
[[nodiscard]] virtual bool Init(std::string licenseKey, std::string projectDirectory, std::string engineDirectory, std::string modelTemplateDirectory, std::string modelZipPassword, bool isLatestEngine)=0;
[[nodiscard]] virtual std::vector<std::string> GetProjects()=0;// Return a list of projects in the project directory
[[nodiscard]] virtual std::vector<std::string> GetProjectExperiments(std::string projectName)=0;// Return a list of experiments for a specific project
[[nodiscard]] virtual bool CreateProject(std::string projectName) = 0;
[[nodiscard]] virtual bool DeleteProject(std::string projectName)=0;
[[nodiscard]] virtual bool SetWorkingDirectory(std::string workingDirectory)=0;
[[nodiscard]] virtual bool UploadTrainingData(std::string projectName)=0; // Upload the training data to the project
[[nodiscard]] virtual bool CreateTrainingEngine(std::string projectName, int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate)=0;// extractorType =0: FAST, 1: ACCURATE; 2: VERY ACCURATE
[[nodiscard]] virtual std::string GetProjectExperimentStatus(std::string projectName, int experimentNumber)=0;// Return the status of a specific experiment
[[nodiscard]] virtual std::string GenerateTrainingCommand(std::string projectName, int experimentNumber, int extractorType)=0; //Generate the training command
[[nodiscard]] virtual std::string GenerateCustomTrainingCommand(std::string projectName, int experimentNumber, int extractorType, std::string pretrainModel) = 0; //Generate the training command
[[nodiscard]] virtual std::string GenerateEvaluateModelCommand(std::string projectName, int experimentNumber, bool& zipModelExist)=0; //Evaluate the accuracy of the model
[[nodiscard]] virtual std::string EvaluateModel(std::string projectName, int experimentNumber)=0; //Evaluate the accuracy of the model
[[nodiscard]] virtual bool DownloadModel(std::string projectName, int experimentNumber, std::string destZipDirectory, int modelModel = 0)=0;
[[nodiscard]] virtual std::string ParseTrainingResults(std::string trainingResults)=0;
[[nodiscard]] virtual bool CheckEngineStatus() = 0;
[[nodiscard]] virtual bool CheckEngine() = 0;
[[nodiscard]] virtual std::string GenerateTestCommand(std::string projectName, int experimentNumber, bool& zipModelExist, const std::string& testDataFolder) = 0; //Generate the test command
[[nodiscard]] std::string GetProjectDirectory() { return _projectDirectory; }
[[nodiscard]] bool ZipExperiment(std::string projectName, int experimentNumber);
[[nodiscard]] bool IsProcessRunning(const char* processName);
[[nodiscard]] double ParseObjectDetectionMAP(std::string stEvaluationResult);
[[nodiscard]] std::string GetLatestValidFolderAndDeleteOthers(const std::string& projectName, const std::string& rootPath);
protected:
std::string _licenseKey;
bool _isLicenseValid{ false };
bool _changeProjectDirectory{ false };
bool _isLatestEngine{ false }; // If the engine is the latest version. For example, Object Detection uses Yolov10
std::string _zipPassword;
std::string _modelZipPassword;
std::string _projectDirectory; // Project directory C:\ProgramData\Sh7O7nUe7vJ
std::string _engineDirectory; // C:\ProgramData\mt5P9nTe5vG\Engine\CUDA11 (will be replaced by ANS Runtime Engine)
std::string _modelTemplateDirectory; // C:\ProgramData\mt5P9nTe5vG\Engine\CUDA11 (could be in the same data folder of the installation folder)
std::string _workingDirectory; // C:\Programs\AITraining\Mask (the current project working directory)
std::string _projectName; //
int _currentExperimentNumber{ 0 }; //
SPDLogger& _logger = SPDLogger::GetInstance("ANSTRE", false);
std::vector<std::string> _projects;
std::string ExecuteCommand(const char* cmd);
std::vector<std::string> ParseANSClass(const std::string& ansClassFileName);
std::string ConvertVectorToClass(const std::vector<std::string>& vec);
};
}
// trainingEngineType =0: ODHUB, =1: Object Detection, =2: Classification, =3: Segmentation; =4: Abnomally Detection
extern "C" ANSTRE_API int CreateANSTREHandle(ANSCENTER::ANSTRE** Handle, const char* licenseKey, const char* projectDirectory, const char* engineDirectory, const char* modelTemplateDirectory, const char* modelZipPassword, int trainingEngineType, int latestEngine);
extern "C" ANSTRE_API int ReleaseANSTREHandle(ANSCENTER::ANSTRE** Handle);
extern "C" ANSTRE_API int ANSTRE_GetProjects(ANSCENTER::ANSTRE** Handle, LStrHandle strProjects);
extern "C" ANSTRE_API int ANSTRE_GetProjectExperiments(ANSCENTER::ANSTRE** Handle, const char* projectName, LStrHandle strProjectExperiments);
extern "C" ANSTRE_API int ANSTRE_CreateProject(ANSCENTER::ANSTRE** Handle, const char* projectName);
extern "C" ANSTRE_API int ANSTRE_DeleteProject(ANSCENTER::ANSTRE** Handle, const char* projectName);
extern "C" ANSTRE_API int ANSTRE_SetWorkingDirectory(ANSCENTER::ANSTRE** Handle, const char* workingDirectory);
extern "C" ANSTRE_API int ANSTRE_UploadTrainingData(ANSCENTER::ANSTRE** Handle, const char* projectName);
extern "C" ANSTRE_API int ANSTRE_CreateTrainingEngine(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate);
extern "C" ANSTRE_API int ANSTRE_GetProjectExperimentStatus(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, LStrHandle projectStatus);
extern "C" ANSTRE_API int ANSTRE_GenerateTrainingCommand(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, int extractorType, LStrHandle trainingCommand);
extern "C" ANSTRE_API int ANSTRE_GenerateCustomTrainingCommand(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, int extractorType, const char* pretrainedModel,LStrHandle trainingCommand);
extern "C" ANSTRE_API int ANSTRE_EvaluateModel(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, LStrHandle mAPResult);
extern "C" ANSTRE_API int ANSTRE_EvaluateModelOnTestData(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, const char* dataFolder, LStrHandle evaluationCommand);
extern "C" ANSTRE_API int ANSTRE_DownloadModel(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, const char* downloadDirDestination, int modelMode);
extern "C" ANSTRE_API int ANSTRE_GetProjectDirectory(ANSCENTER::ANSTRE** Handle, LStrHandle strProjectDir);
extern "C" ANSTRE_API int ANSTRE_ZipExperiment(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber);
extern "C" ANSTRE_API double ANSTRE_ParseMAP(ANSCENTER::ANSTRE** Handle, const char* evaluationResult);
extern "C" ANSTRE_API int ANSTRE_ParseTrainingResults(ANSCENTER::ANSTRE** Handle, const char* trainingResult, LStrHandle strResult);
extern "C" ANSTRE_API int ANSTRE_CheckEngineStatus(ANSCENTER::ANSTRE** Handle);
extern "C" ANSTRE_API int ANSTRE_CheckEngine(ANSCENTER::ANSTRE** Handle);
//C++ API
extern "C" ANSTRE_API int ANSTRE_GetProjects_CPP(ANSCENTER::ANSTRE** Handle, std::string& strProjects);
extern "C" ANSTRE_API int ANSTRE_GetProjectExperiments_CPP(ANSCENTER::ANSTRE** Handle, const char* projectName, std::string& strProjectExperiments);
extern "C" ANSTRE_API int ANSTRE_GetProjectExperimentStatus_CPP(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, std::string& projectStatus);
extern "C" ANSTRE_API int ANSTRE_GenerateTrainingCommand_CPP(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, int extractorType, std::string& trainingCommand);
extern "C" ANSTRE_API int ANSTRE_GenerateCustomTrainingCommand_CPP(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, int extractorType, const char* pretrainedModel, std::string& trainingCommand);
extern "C" ANSTRE_API int ANSTRE_EvaluateModel_CPP(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, std::string& mAPResult);
extern "C" ANSTRE_API int ANSTRE_EvaluateModelOnTestData_CPP(ANSCENTER::ANSTRE** Handle, const char* projectName, int experimentNumber, const char* dataFolder,std::string& evaluationCommand);
extern "C" ANSTRE_API int ANSTRE_GetProjectDirectory_CPP(ANSCENTER::ANSTRE** Handle, std::string& strProjectDir);
extern "C" ANSTRE_API int ANSTRE_ParseTrainingResults_CPP(ANSCENTER::ANSTRE** Handle, const char* trainingResult, std::string& strResult);
// V2 API — accepts uint64_t handleVal by value (LabVIEW handle-by-value fix)
extern "C" ANSTRE_API int ANSTRE_GetProjects_V2(uint64_t handleVal, LStrHandle strProjects);
extern "C" ANSTRE_API int ANSTRE_GetProjectExperiments_V2(uint64_t handleVal, const char* projectName, LStrHandle strProjectExperiments);
extern "C" ANSTRE_API int ANSTRE_CreateProject_V2(uint64_t handleVal, const char* projectName);
extern "C" ANSTRE_API int ANSTRE_DeleteProject_V2(uint64_t handleVal, const char* projectName);
extern "C" ANSTRE_API int ANSTRE_SetWorkingDirectory_V2(uint64_t handleVal, const char* workingDirectory);
extern "C" ANSTRE_API int ANSTRE_UploadTrainingData_V2(uint64_t handleVal, const char* projectName);
extern "C" ANSTRE_API int ANSTRE_CreateTrainingEngine_V2(uint64_t handleVal, const char* projectName, int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate);
extern "C" ANSTRE_API int ANSTRE_GetProjectExperimentStatus_V2(uint64_t handleVal, const char* projectName, int experimentNumber, LStrHandle projectStatus);
extern "C" ANSTRE_API int ANSTRE_GenerateTrainingCommand_V2(uint64_t handleVal, const char* projectName, int experimentNumber, int extractorType, LStrHandle trainingCommand);
extern "C" ANSTRE_API int ANSTRE_GenerateCustomTrainingCommand_V2(uint64_t handleVal, const char* projectName, int experimentNumber, int extractorType, const char* pretrainedModel, LStrHandle trainingCommand);
extern "C" ANSTRE_API int ANSTRE_EvaluateModel_V2(uint64_t handleVal, const char* projectName, int experimentNumber, LStrHandle mAPResult);
extern "C" ANSTRE_API int ANSTRE_EvaluateModelOnTestData_V2(uint64_t handleVal, const char* projectName, int experimentNumber, const char* dataFolder, LStrHandle evaluationCommand);
extern "C" ANSTRE_API int ANSTRE_DownloadModel_V2(uint64_t handleVal, const char* projectName, int experimentNumber, const char* downloadDirDestination, int modelMode);
extern "C" ANSTRE_API int ANSTRE_GetProjectDirectory_V2(uint64_t handleVal, LStrHandle strProjectDir);
extern "C" ANSTRE_API int ANSTRE_ZipExperiment_V2(uint64_t handleVal, const char* projectName, int experimentNumber);
extern "C" ANSTRE_API double ANSTRE_ParseMAP_V2(uint64_t handleVal, const char* evaluationResult);
extern "C" ANSTRE_API int ANSTRE_ParseTrainingResults_V2(uint64_t handleVal, const char* trainingResult, LStrHandle strResult);
extern "C" ANSTRE_API int ANSTRE_CheckEngineStatus_V2(uint64_t handleVal);
extern "C" ANSTRE_API int ANSTRE_CheckEngine_V2(uint64_t handleVal);
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,45 @@
#ifndef ANSYLCLTRE_H
#define ANSYLCLTRE_H
#pragma once
#include "ANSTrainingEngine.h"
namespace ANSCENTER {
class ANSTRE_API ANYLCLTRE :public ANSTRE {
public:
ANYLCLTRE();
~ANYLCLTRE();
[[nodiscard]] bool Init(std::string licenseKey, std::string projectDirectory, std::string engineDirectory, std::string modelTemplateDirectory, std::string modelZipPassword, bool isLatestEngine)override;
[[nodiscard]] std::vector<std::string> GetProjects()override;// Return a list of projects in the project directory
[[nodiscard]] std::vector<std::string> GetProjectExperiments(std::string projectName)override;// Return a list of experiments for a specific project
[[nodiscard]] bool CreateProject(std::string projectName)override;
[[nodiscard]] bool DeleteProject(std::string projectName)override;
[[nodiscard]] bool SetWorkingDirectory(std::string workingDirectory)override;
[[nodiscard]] bool UploadTrainingData(std::string projectName)override; // Upload the training data to the project
[[nodiscard]] bool CreateTrainingEngine(std::string projectName, int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate)override;// extractorType =0: FAST, 1: ACCURATE; 2: VERY ACCURATE
[[nodiscard]] std::string GetProjectExperimentStatus(std::string projectName, int experimentNumber)override;// Return the status of a specific experiment
[[nodiscard]] std::string GenerateTrainingCommand(std::string projectName, int experimentNumber, int extractorType)override; //Generate the training command
[[nodiscard]] std::string GenerateCustomTrainingCommand(std::string projectName, int experimentNumber, int extractorType, std::string pretrainedModel)override; //Generate the training command
[[nodiscard]] std::string GenerateEvaluateModelCommand(std::string projectName, int experimentNumber, bool& zipModelExist)override; //Evaluate the accuracy of the model
[[nodiscard]] std::string EvaluateModel(std::string projectName, int experimentNumber)override; //Evaluate the accuracy of the model
[[nodiscard]] bool DownloadModel(std::string projectName, int experimentNumber, std::string destZipDirectory, int modelModel = 0)override;
[[nodiscard]] std::string ParseTrainingResults(std::string trainingResults)override;
[[nodiscard]] bool CheckEngineStatus() override;
[[nodiscard]] bool CheckEngine() override;
[[nodiscard]] std::string GenerateTestCommand(std::string projectName, int experimentNumber, bool& zipModelExist, const std::string& testDataFolder)override; //Generate the test command
private:
std::string yolo11nModelFile;
std::string ParseMAP(const std::string& text);
std::string AdjustRootDirectory(const std::string& root);
std::string GenerateClassNames(std::string labelMapFile);
std::map<std::string, std::string> ExtractDataFromCfgFile(const std::string& filePath);
void GenerateTrainDataSet(const std::string& sourceFolder,std::string projectDir, double trainRatio = 0.8); // create train and test folders
bool GenerateConfigFile(const std::string& templateFile,
const std::string& outputFile,
const std::map<std::string, std::string>& replacements);
int ReadClassesValue(const std::string& filePath);
int GenerateClassNamesFile(std::string labelMapFile, std::string objectDataFile);
void CheckLicense();
void DeleteWeightsFiles(const std::string& folderPath);
};
}
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,46 @@
#ifndef ANSYLOBBTRE_H
#define ANSYLOBBTRE_H
#pragma once
#include "ANSTrainingEngine.h"
namespace ANSCENTER {
class ANSTRE_API ANYLOBBTRE :public ANSTRE {
public:
ANYLOBBTRE();
~ANYLOBBTRE();
[[nodiscard]] bool Init(std::string licenseKey, std::string projectDirectory, std::string engineDirectory, std::string modelTemplateDirectory, std::string modelZipPassword, bool isLatestEngine)override;
[[nodiscard]] std::vector<std::string> GetProjects()override;// Return a list of projects in the project directory
[[nodiscard]] std::vector<std::string> GetProjectExperiments(std::string projectName)override;// Return a list of experiments for a specific project
[[nodiscard]] bool CreateProject(std::string projectName)override;
[[nodiscard]] bool DeleteProject(std::string projectName)override;
[[nodiscard]] bool SetWorkingDirectory(std::string workingDirectory)override;
[[nodiscard]] bool UploadTrainingData(std::string projectName)override; // Upload the training data to the project
[[nodiscard]] bool CreateTrainingEngine(std::string projectName, int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate)override;// extractorType =0: FAST, 1: ACCURATE; 2: VERY ACCURATE
[[nodiscard]] std::string GetProjectExperimentStatus(std::string projectName, int experimentNumber)override;// Return the status of a specific experiment
[[nodiscard]] std::string GenerateTrainingCommand(std::string projectName, int experimentNumber, int extractorType)override; //Generate the training command
[[nodiscard]] std::string GenerateCustomTrainingCommand(std::string projectName, int experimentNumber, int extractorType, std::string pretrainedModel)override; //Generate the training command
[[nodiscard]] std::string GenerateEvaluateModelCommand(std::string projectName, int experimentNumber, bool& zipModelExist)override; //Evaluate the accuracy of the model
[[nodiscard]] std::string EvaluateModel(std::string projectName, int experimentNumber)override; //Evaluate the accuracy of the model
[[nodiscard]] bool DownloadModel(std::string projectName, int experimentNumber, std::string destZipDirectory, int modelModel = 0)override;
[[nodiscard]] std::string ParseTrainingResults(std::string trainingResults)override;
[[nodiscard]] bool CheckEngineStatus() override;
[[nodiscard]] bool CheckEngine() override;
[[nodiscard]] std::string GenerateTestCommand(std::string projectName, int experimentNumber, bool& zipModelExist, const std::string& testDataFolder)override; //Generate the test command
private:
std::string yolo11nModelFile;
std::string ParseMAP(const std::string& text);
std::string AdjustRootDirectory(const std::string& root);
std::string GenerateClassNames(std::string labelMapFile);
std::map<std::string, std::string> ExtractDataFromCfgFile(const std::string& filePath);
bool GenerateObjectDataFile(std::string sourcePbDataPath, std::string objectDataFile, bool useANSClassFile=false);
void GenerateTrainDataSet(const std::string& sourceFolder, const std::string& trainFolder, const std::string& testFolder, double trainRatio = 0.8);
bool GenerateConfigFile(const std::string& templateFile,
const std::string& outputFile,
const std::map<std::string, std::string>& replacements);
int ReadClassesValue(const std::string& filePath);
int GenerateClassNamesFile(std::string labelMapFile, std::string objectDataFile, bool useANSClassFile);
void CheckLicense();
void DeleteWeightsFiles(const std::string& folderPath);
};
}
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,46 @@
#ifndef ANSYLSEGTRE_H
#define ANSYLSEGTRE_H
#pragma once
#include "ANSTrainingEngine.h"
namespace ANSCENTER {
class ANSTRE_API ANYLSEGTRE :public ANSTRE {
public:
ANYLSEGTRE();
~ANYLSEGTRE();
[[nodiscard]] bool Init(std::string licenseKey, std::string projectDirectory, std::string engineDirectory, std::string modelTemplateDirectory, std::string modelZipPassword, bool isLatestEngine)override;
[[nodiscard]] std::vector<std::string> GetProjects()override;// Return a list of projects in the project directory
[[nodiscard]] std::vector<std::string> GetProjectExperiments(std::string projectName)override;// Return a list of experiments for a specific project
[[nodiscard]] bool CreateProject(std::string projectName)override;
[[nodiscard]] bool DeleteProject(std::string projectName)override;
[[nodiscard]] bool SetWorkingDirectory(std::string workingDirectory)override;
[[nodiscard]] bool UploadTrainingData(std::string projectName)override; // Upload the training data to the project
[[nodiscard]] bool CreateTrainingEngine(std::string projectName, int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate)override;// extractorType =0: FAST, 1: ACCURATE; 2: VERY ACCURATE
[[nodiscard]] std::string GetProjectExperimentStatus(std::string projectName, int experimentNumber)override;// Return the status of a specific experiment
[[nodiscard]] std::string GenerateTrainingCommand(std::string projectName, int experimentNumber, int extractorType)override; //Generate the training command
[[nodiscard]] std::string GenerateCustomTrainingCommand(std::string projectName, int experimentNumber, int extractorType, std::string pretrainedModel)override; //Generate the training command
[[nodiscard]] std::string GenerateEvaluateModelCommand(std::string projectName, int experimentNumber, bool& zipModelExist)override; //Evaluate the accuracy of the model
[[nodiscard]] std::string EvaluateModel(std::string projectName, int experimentNumber)override; //Evaluate the accuracy of the model
[[nodiscard]] bool DownloadModel(std::string projectName, int experimentNumber, std::string destZipDirectory, int modelModel = 0)override;
[[nodiscard]] std::string ParseTrainingResults(std::string trainingResults)override;
[[nodiscard]] bool CheckEngineStatus() override;
[[nodiscard]] bool CheckEngine() override;
[[nodiscard]] std::string GenerateTestCommand(std::string projectName, int experimentNumber, bool& zipModelExist, const std::string& testDataFolder)override; //Generate the test command
private:
std::string yolo11nModelFile;
std::string ParseMAP(const std::string& text);
std::string AdjustRootDirectory(const std::string& root);
std::string GenerateClassNames(std::string labelMapFile);
std::map<std::string, std::string> ExtractDataFromCfgFile(const std::string& filePath);
bool GenerateObjectDataFile(std::string sourcePbDataPath, std::string objectDataFile, bool useANSClassFile);
void GenerateTrainDataSet(const std::string& sourceFolder, const std::string& trainFolder, const std::string& testFolder, double trainRatio = 0.8);
bool GenerateConfigFile(const std::string& templateFile,
const std::string& outputFile,
const std::map<std::string, std::string>& replacements);
int ReadClassesValue(const std::string& filePath);
int GenerateClassNamesFile(std::string labelMapFile, std::string objectDataFile, bool useANSClassFile=false);
void CheckLicense();
void DeleteWeightsFiles(const std::string& folderPath);
};
}
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,46 @@
#ifndef ANSYLTRE_H
#define ANSYLTRE_H
#pragma once
#include "ANSTrainingEngine.h"
namespace ANSCENTER {
class ANSTRE_API ANYLTRE:public ANSTRE {
public:
ANYLTRE();
~ANYLTRE();
[[nodiscard]] bool Init(std::string licenseKey, std::string projectDirectory, std::string engineDirectory, std::string modelTemplateDirectory, std::string modelZipPassword, bool isLatestEngine)override;
[[nodiscard]] std::vector<std::string> GetProjects()override;// Return a list of projects in the project directory
[[nodiscard]] std::vector<std::string> GetProjectExperiments(std::string projectName)override;// Return a list of experiments for a specific project
[[nodiscard]] bool CreateProject(std::string projectName)override;
[[nodiscard]] bool DeleteProject(std::string projectName)override;
[[nodiscard]] bool SetWorkingDirectory(std::string workingDirectory)override;
[[nodiscard]] bool UploadTrainingData(std::string projectName)override; // Upload the training data to the project
[[nodiscard]] bool CreateTrainingEngine(std::string projectName, int experimentNumber, int extractorType, long numberStep, int batchSize, double learningRate)override;// extractorType =0: FAST, 1: ACCURATE; 2: VERY ACCURATE
[[nodiscard]] std::string GetProjectExperimentStatus(std::string projectName, int experimentNumber)override;// Return the status of a specific experiment
[[nodiscard]] std::string GenerateTrainingCommand(std::string projectName, int experimentNumber, int extractorType)override; //Generate the training command
[[nodiscard]] std::string GenerateCustomTrainingCommand(std::string projectName, int experimentNumber, int extractorType, std::string pretrainedModel)override; //Generate the training command
[[nodiscard]] std::string GenerateEvaluateModelCommand(std::string projectName, int experimentNumber, bool& zipModelExist)override; //Evaluate the accuracy of the model
[[nodiscard]] std::string EvaluateModel(std::string projectName, int experimentNumber)override; //Evaluate the accuracy of the model
[[nodiscard]] bool DownloadModel(std::string projectName, int experimentNumber, std::string destZipDirectory, int modelModel=0)override;
[[nodiscard]] std::string ParseTrainingResults(std::string trainingResults)override;
[[nodiscard]] bool CheckEngineStatus() override;
[[nodiscard]] bool CheckEngine() override;
[[nodiscard]] std::string GenerateTestCommand(std::string projectName, int experimentNumber, bool& zipModelExist, const std::string& testDataFolder)override; //Generate the test command
private:
std::string yolo11nModelFile;
std::string ParseMAP(const std::string& text);
std::string AdjustRootDirectory(const std::string& root);
std::string GenerateClassNames(std::string labelMapFile);
std::map<std::string, std::string> ExtractDataFromCfgFile(const std::string& filePath);
bool GenerateObjectDataFile(std::string sourcePbDataPath, std::string objectDataFile, bool useANSClassFile=false);
void GenerateTrainDataSet(const std::string& sourceFolder, const std::string& trainFolder, const std::string& testFolder, double trainRatio = 0.8);
bool GenerateConfigFile(const std::string& templateFile,
const std::string& outputFile,
const std::map<std::string, std::string>& replacements);
int ReadClassesValue(const std::string& filePath);
int GenerateClassNamesFile(std::string labelMapFile, std::string objectDataFile, bool useANSClassFile);
void CheckLicense();
void DeleteWeightsFiles(const std::string& folderPath);
};
}
#endif

View File

@@ -0,0 +1,24 @@
# ANSTrainingEngine — Training Engine DLL
file(GLOB ANSTRE_HEADERS "*.h")
file(GLOB ANSTRE_SOURCES "*.cpp")
add_library(ANSTrainingEngine SHARED ${ANSTRE_HEADERS} ${ANSTRE_SOURCES})
target_include_directories(ANSTrainingEngine PUBLIC
${CMAKE_CURRENT_SOURCE_DIR}
${SHARED_INCLUDE_DIR}
)
target_link_libraries(ANSTrainingEngine
PRIVATE ANSLicensingSystem
PRIVATE anslicensing
PRIVATE labview
PRIVATE boost
)
target_compile_definitions(ANSTrainingEngine PRIVATE UNICODE _UNICODE
ANSODTRAININGENGINE_EXPORTS
_USRDLL
)
target_precompile_headers(ANSTrainingEngine PRIVATE pch.h)

View File

@@ -0,0 +1,19 @@
// dllmain.cpp : Defines the entry point for the DLL application.
#include "pch.h"
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}

View File

@@ -0,0 +1,7 @@
#pragma once
#define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers
#define NOMINMAX // Prevent windows.h from defining min/max macros
// which break std::min / std::max (C2589)
// Windows Header Files
#include <windows.h>

View File

@@ -0,0 +1,5 @@
// pch.cpp: source file corresponding to the pre-compiled header
#include "pch.h"
// When you are using pre-compiled headers, this source file is necessary for compilation to succeed.

View File

@@ -0,0 +1,13 @@
// pch.h: This is a precompiled header file.
// Files listed below are compiled only once, improving build performance for future builds.
// This also affects IntelliSense performance, including code completion and many code browsing features.
// However, files listed here are ALL re-compiled if any one of them is updated between builds.
// Do not add files here that you will be updating frequently as this negates the performance advantage.
#ifndef PCH_H
#define PCH_H
// add headers that you want to pre-compile here
#include "framework.h"
#endif //PCH_H