Train_Identify_arm/ai_matrix/myutils/myutils.cpp

822 lines
24 KiB
C++
Raw Normal View History

2024-06-19 06:35:05 +00:00
#include "myutils.h"
namespace ai_matrix
{
const int TIME_DIFF = 28800; // 8 hour
MyUtils *MyUtils::ins = nullptr;
MyUtils::GarbageCollector MyUtils::gc;
std::mutex MyUtils::mx;
MyUtils *MyUtils::getins()
{
//双层锁,确保线程安全
if (ins == nullptr)
{
std::lock_guard<std::mutex> guard(mx); //防止异常发生不能解锁
if (ins == nullptr)
{
ins = new MyUtils();
}
}
return ins;
}
float MyUtils::getMean(const std::vector<float> &data)
{
int size = data.size();
if (size == 0)
{
return 0;
}
float sum = 0;
for (int i = 0; i < size; i++)
{
sum += data[i];
}
return sum / size;
}
float MyUtils::getMax(const std::vector<float> &data)
{
int size = data.size();
if (size == 0)
{
return 0;
}
float max = 0;
for (int i = 0; i < size; i++)
{
if (i == 0)
{
max = data[i];
}
else if (data[i] > max)
{
max = data[i];
}
}
return max;
}
float MyUtils::getMin(const std::vector<float> &data)
{
int size = data.size();
if (size == 0)
{
return 0;
}
float min = 0;
for (int i = 0; i < size; i++)
{
if (i == 0)
{
min = data[i];
}
else if (data[i] < min)
{
min = data[i];
}
}
return min;
}
float MyUtils::getMedian(const std::vector<float> &data)
{
if (data.size() < 2)
{
return 0;
}
std::vector<float> data_tmp;
int n = data.size();
for (int i = 0; i < n; i++)
{
data_tmp.push_back(data[i]);
}
std::sort(data_tmp.begin(), data_tmp.end(), std::less<float>());
if (n % 2 == 0)
{
return (data_tmp[n / 2] + data_tmp[n / 2 - 1]) / 2;
}
else
{
return data_tmp[(n - 1) / 2];
}
}
std::string MyUtils::get_timestamp_file()
{
time_t timep = time(NULL);
struct tm *p = localtime(&timep);
struct timeval tv;
gettimeofday(&tv, NULL);
int msec = tv.tv_usec / 1000;
char tmp[30] = {0};
sprintf(tmp, "%04d-%02d-%02d-%02d-%02d-%02d-%03d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday, p->tm_hour, p->tm_min, p->tm_sec, msec);
return std::string(tmp);
}
std::string MyUtils::get_date()
{
time_t timep = time(NULL);
struct tm *p = localtime(&timep);
struct timeval tv;
gettimeofday(&tv, NULL);
int msec = tv.tv_usec / 1000;
char tmp[12] = { 0 };
sprintf(tmp, "%04d-%02d-%02d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday);
return std::string(tmp);
}
std::string MyUtils::get_time()
{
time_t timep = time(NULL);
struct tm *p = localtime(&timep);
struct timeval tv;
gettimeofday(&tv, NULL);
int msec = tv.tv_usec / 1000;
char tmp[10] = { 0 };
sprintf(tmp, "%02d-%02d-%02d", p->tm_hour, p->tm_min, p->tm_sec);
return std::string(tmp);
}
std::string MyUtils::get_timestamp_log()
{
time_t timep = time(NULL);
struct tm *p = localtime(&timep);
struct timeval tv;
gettimeofday(&tv, NULL);
int msec = tv.tv_usec / 1000;
char tmp[30] = {0};
sprintf(tmp, "%04d-%02d-%02d %02d:%02d:%02d.%03d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday, p->tm_hour, p->tm_min, p->tm_sec, msec);
return std::string(tmp);
}
std::string MyUtils::create_dir_name(std::string root, std::string name)
{
std::string dir_path = root + "/" + name;
if (access(dir_path.c_str(), F_OK) != 0)
{
if (mkdir(dir_path.c_str(), 0755) != 0) //如果父目录不存在,会创建失败
{
perror("mkdir fail");
return "";
}
}
return dir_path;
}
std::string MyUtils::create_dir_date(std::string root)
{
time_t timep = time(NULL);
struct tm *p = localtime(&timep);
char tmp_date[20] = {0};
sprintf(tmp_date, "%04d-%02d-%02d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday);
std::string dir_path;
dir_path = root + "/" + std::string(tmp_date); //创建日期目录
if (access(dir_path.c_str(), F_OK) != 0)
{
if (mkdir(dir_path.c_str(), 0755) != 0) //如果父目录不存在,会创建失败
{
perror("mkdir fail");
return "";
}
}
return dir_path;
}
std::string MyUtils::create_dir_date_name_time(std::string root, std::string name)
{
time_t timep = time(NULL);
struct tm *p = localtime(&timep);
char tmp_date[20] = {0};
sprintf(tmp_date, "%04d-%02d-%02d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday);
char tmp_time[20] = {0};
sprintf(tmp_time, "%02d-%02d-%02d", p->tm_hour, p->tm_min, p->tm_sec);
std::string dir_path;
dir_path = root + "/" + std::string(tmp_date); //创建日期目录
if (access(dir_path.c_str(), F_OK) != 0)
{
if (mkdir(dir_path.c_str(), 0755) != 0) //如果父目录不存在,会创建失败
{
perror("mkdir fail");
return "";
}
}
dir_path = dir_path + "/" + name + "_" + std::string(tmp_time); //创建点云目录
if (access(dir_path.c_str(), F_OK) != 0)
{
if (mkdir(dir_path.c_str(), 0755) != 0) //如果父目录不存在,会创建失败
{
perror("mkdir fail");
return "";
}
}
return dir_path;
}
std::string MyUtils::create_file_path(std::string root, std::string name, std::string suffix)
{
time_t timep = time(NULL);
struct tm *p = localtime(&timep);
char tmp_date[20] = {0};
sprintf(tmp_date, "%04d-%02d-%02d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday);
char tmp_time[20] = {0};
sprintf(tmp_time, "%02d-%02d-%02d", p->tm_hour, p->tm_min, p->tm_sec);
std::string file_path;
file_path = root + "/" + std::string(tmp_date); //创建日期目录
if (access(file_path.c_str(), F_OK) != 0)
{
if (mkdir(file_path.c_str(), 0755) != 0) //如果父目录不存在,会创建失败
{
perror("mkdir fail");
return "";
}
}
file_path = file_path + "/" + name + "_" + std::string(tmp_time) + suffix; //创建文件
return file_path;
}
//字符串分割函数
std::vector<std::string> MyUtils::split(std::string str, std::string pattern)
{
std::string::size_type pos;
std::vector<std::string> result;
str += pattern; //扩展字符串以方便操作
int size = str.size();
for (int i = 0; i < size; i++)
{
pos = str.find(pattern, i);
if (pos < size)
{
std::string s = str.substr(i, pos - i);
result.push_back(s);
i = pos + pattern.size() - 1;
}
}
return result;
}
std::string MyUtils::getStringFromFloat(float f)
{
std::ostringstream buffer;
buffer << f;
return buffer.str();
}
std::string MyUtils::getStringFromBool(bool b)
{
std::ostringstream buffer;
buffer << b;
return buffer.str();
}
/**
*
* @param filePath
* @param savePath
* @return
*/
bool MyUtils::copyFile(std::string filePath, std::string savePath)
{
FILE *fp, *sp;
fp = fopen(filePath.c_str(), "rb");
sp = fopen(savePath.c_str(), "w+b");
if (!fp || !sp)
{
LogError << "open fial filePath:" << filePath << " or savePath:" << savePath;
return false;
}
void *buffer;
while (!feof(fp))
{
fread(&buffer, 1, 1, fp);
fwrite(&buffer, 1, 1, sp);
}
fclose(fp);
fclose(sp);
return true;
}
std::string& MyUtils::replace_all_distinct(std::string &str, const std::string &old_value, const std::string &new_value)
{
for (std::string::size_type pos(0); pos != std::string::npos; pos += new_value.length()) {
if ((pos = str.find(old_value, pos)) != std::string::npos)
str.replace(pos, old_value.length(), new_value);
else break;
}
return str;
}
/**
*
* inParam : N/A
* outParam: N/A
* return :
*/
std::string MyUtils::GetDate()
{
struct timeval time = {0, 0};
gettimeofday(&time, nullptr);
time_t timep = time.tv_sec + TIME_DIFF;
struct tm *p = gmtime(&timep);
char szTmp[12] = {0};
sprintf(szTmp, "%04d-%02d-%02d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday);
return std::string(szTmp);
}
/**
*
* inParam : N/A
* outParam: N/A
* return :
*/
std::string MyUtils::GetTime()
{
struct timeval time = {0, 0};
gettimeofday(&time, nullptr);
time_t timep = time.tv_sec + TIME_DIFF;
struct tm *p = gmtime(&timep);
char szTmp[10] = {0};
sprintf(szTmp, "%02d-%02d-%02d", p->tm_hour, p->tm_min, p->tm_sec);
return std::string(szTmp);
}
//时间戳转化为时间 毫秒级
std::string MyUtils::Stamp2Time(long long timestamp, bool has_msec)
{
int ms = timestamp % 1000;//取毫秒
time_t tick = (time_t)(timestamp/1000);//转换时间
struct tm tm;
char s[40];
tm = *localtime(&tick);
strftime(s, sizeof(s), "%Y-%m-%d %H:%M:%S", &tm);
std::string str(s);
if (has_msec)
{
str = str+ "." + std::to_string(ms);
}
return str;
}
/**
* 1970
* inParam : N/A
* outParam: N/A
* return :
*/
uint64_t MyUtils::GetCurrentTimeMillis()
{
struct timeval tv;
gettimeofday(&tv, NULL);
//printf("tv_sec:%ld, tv_usec:%ld\n", tv.tv_sec, tv.tv_usec);
return tv.tv_sec * 1000 + tv.tv_usec / 1000;
}
/**
* 1970 (YYYY-MM-DD hh-mm-ss)
* inParam : std::string &strDateTime
* outParam: N/A
* return :
*/
uint64_t MyUtils::GetParamTimeMilliSeconds(std::string &strDateTime)
{
LogDebug << "strDateTime:" << strDateTime;
if (strDateTime.length() != 19)
{
return 0;
}
int iYear = atoi(strDateTime.substr(0, 4).c_str());
int iMon = atoi(strDateTime.substr(5, 2).c_str());
int iDay = atoi(strDateTime.substr(8, 2).c_str());
int iHour = atoi(strDateTime.substr(11, 2).c_str());
int iMin = atoi(strDateTime.substr(14, 2).c_str());
int iSec = atoi(strDateTime.substr(17, 2).c_str());
struct tm stm;
memset(&stm, 0, sizeof(stm));
stm.tm_year = iYear - 1900;
stm.tm_mon = iMon - 1;
stm.tm_mday = iDay;
stm.tm_hour = iHour;
stm.tm_min = iMin;
stm.tm_sec = iSec;
uint64_t i64Ret = (uint64_t)mktime(&stm) * 1000;
LogDebug << iYear << " " << iMon << " " << iDay << " " << iHour << " " << iMin << " " << iSec << " " << i64Ret;
return i64Ret;
}
/**
* Anchor行分割
* inParam : std::string &strLine Anchor一行内容
* : const std::set<char> &setDelimiters
* outParam: N/A
* return :
*/
std::vector<float> MyUtils::SplitAnchor(std::string &strLine, const std::set<char> &setDelimiters)
{
std::vector<float> result;
if (strLine.empty())
{
return result;
}
char const *pch = strLine.c_str();
char const *start = pch;
for (; *pch; ++pch)
{
if (setDelimiters.find(*pch) != setDelimiters.end())
{
if (start != pch)
{
std::string tmp(start, pch);
result.push_back(atof(tmp.c_str())); //浮点数
}
start = pch + 1;
}
}
result.push_back(atof(start)); //最后一个内容
return result;
}
/**
*
* inParam : std::string strDirPath :
* outParam: N/A
* return : true/false
*/
bool MyUtils::CreateDirPath(std::string strDirPath)
{
if (strDirPath.back() != '/')
{
strDirPath += "/";
}
if (access(strDirPath.c_str(), F_OK) == 0)
{
return true;
}
std::string::size_type pos = strDirPath.find('/');
while (pos != std::string::npos)
{
std::string strCur = strDirPath.substr(0, pos);
if (!strCur.empty() && access(strCur.c_str(), F_OK) != 0)
{
if (mkdir(strCur.c_str(), 0755) != 0) //如果父目录不存在,会创建失败
{
perror("mkdir fail");
return false;
}
if (chmod(strCur.c_str(), 0777) != 0)
{
perror("chmod fail");
}
}
pos = strDirPath.find('/', pos + 1);
}
return true;
}
#ifdef ASCEND
/**
* Device数据到Host
* inParam : void *pDeviceBuffer device内存地址
: uint32_t iBufferSize device内存大小
* outParam: std::shared_ptr<void> *pHostData host内存地址 (size同入参)
* return : N/A
*/
bool MyUtils::MemcpyDeviceToHost(std::shared_ptr<void> *pHostData, const void *pDeviceBuffer, uint32_t iBufferSize)
{
if (pDeviceBuffer == nullptr || iBufferSize == 0)
{
LogError << "MemcpyDeviceToHost fail pDeviceBuffer is null or iBufferSize is 0";
return false;
}
void *pHostBuffer = nullptr;
int iRet = aclrtMallocHost(&pHostBuffer, iBufferSize);
if (iRet != APP_ERR_OK)
{
LogError << "MemcpyDeviceToHost aclrtMallocHost fail, iBufferSize:" << iBufferSize << " iRet:" << iRet;
return false;
}
pHostData->reset(pHostBuffer, aclrtFreeHost);
iRet = aclrtMemcpy(pHostData->get(), iBufferSize, pDeviceBuffer, iBufferSize, ACL_MEMCPY_DEVICE_TO_HOST);
if (iRet != APP_ERR_OK)
{
LogError << "MemcpyDeviceToHost aclrtMemcpy fail, iBufferSize:" << iBufferSize << " iRet:" << iRet;
return false;
}
return true;
}
/**
* Host数据到Device
* inParam : void *pHostBuffer host内存地址
: uint32_t iBufferSize host内存大小
: bool bDvppFlag 使dvpp方式申请device内存(true)
* outParam: std::shared_ptr<void> *pDeviceData device内存地址 (size同入参)
* return : N/A
*/
bool MyUtils::MemcpyHostToDevice(std::shared_ptr<void> *pDeviceData, const void *pHostBuffer, uint32_t iBufferSize, bool bDvppFlag/*=true*/)
{
if (pHostBuffer == nullptr || iBufferSize == 0)
{
LogError << "MemcpyHostToDevice fail pHostBuffer is null or iBufferSize is 0";
return false;
}
int iRet = APP_ERR_OK;
void *pDeviceBuffer = nullptr;
if (bDvppFlag)
{
int iRet = acldvppMalloc(&pDeviceBuffer, iBufferSize);
if (iRet != APP_ERR_OK)
{
LogError << "MemcpyHostToDevice acldvppMalloc fail, iBufferSize:" << iBufferSize << " iRet:" << iRet;
return false;
}
pDeviceData->reset(pDeviceBuffer, acldvppFree);
}
else
{
int iRet = aclrtMalloc(&pDeviceBuffer, iBufferSize, ACL_MEM_MALLOC_HUGE_FIRST);
if (iRet != APP_ERR_OK)
{
LogError << "MemcpyHostToDevice aclrtMalloc fail, iBufferSize:" << iBufferSize << " iRet:" << iRet;
return false;
}
pDeviceData->reset(pDeviceBuffer, aclrtFree);
}
iRet = aclrtMemcpy(pDeviceData->get(), iBufferSize, pHostBuffer, iBufferSize, ACL_MEMCPY_HOST_TO_DEVICE);
if (iRet != APP_ERR_OK)
{
LogError << "MemcpyHostToDevice aclrtMemcpy fail, iBufferSize:" << iBufferSize << " iRet:" << iRet;
return false;
}
return true;
}
#endif
/**
*
* inParam : uint64_t i64MilliSeconds
* outParam: N/A
* return :
*/
std::string MyUtils::GetDateTimeByMilliSeconds(uint64_t i64MilliSeconds, bool bFormatFlag/*=false*/)
{
time_t timep = i64MilliSeconds / 1000 + TIME_DIFF;
struct tm *p = gmtime(&timep);
char szTmp[32] = {0};
if (bFormatFlag)
{
sprintf(szTmp, "%04d-%02d-%02d %02d:%02d:%02d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday, p->tm_hour, p->tm_min, p->tm_sec);
}
else
{
sprintf(szTmp, "%04d-%02d-%02d %02d-%02d-%02d", 1900 + p->tm_year, 1 + p->tm_mon, p->tm_mday, p->tm_hour, p->tm_min, p->tm_sec);
}
return std::string(szTmp);
}
/**
*
* inParam : std::string &strOneTarget
* outParam: N/A
* return : true/false
*/
bool MyUtils::ChkIsHaveTarget(const std::string &strOneTarget)
{
std::map<int, ai_matrix::DataSourceConfig> mapUseDataSouceCfg = MyYaml::GetIns()->GetUseDataSourceConfig();
bool bFindTarget = false;
for (auto iter = mapUseDataSouceCfg.begin(); iter != mapUseDataSouceCfg.end(); iter++)
{
if (iter->second.strTarget.find(strOneTarget) != std::string::npos)
{
bFindTarget = true;
break;
}
}
return bFindTarget;
}
/**
* json格式文件内容
* inParam : std::string &strFilePath :
* outParam: Json::Value &jvFileInfo :json格式内容
* return : true/false
*/
bool MyUtils::ReadJsonInfo(Json::Value &jvFileInfo, std::string &strFilePath, int iRetry /*=3*/)
{
std::ifstream ifs(strFilePath.c_str());
int i = 0;
while (!ifs.is_open() && i < iRetry)
{
i++;
usleep(10 * 1000);
ifs.open(strFilePath.c_str());
}
if (!ifs.is_open())
{
// LogWarn << "txt:" << strFilePath << " open fail";
return false;
}
std::string strContent;
getline(ifs, strContent);
ifs.close();
Json::CharReaderBuilder jsrBuilder;
std::shared_ptr<Json::CharReader> reader(jsrBuilder.newCharReader());
JSONCPP_STRING errs;
if (!reader->parse(strContent.data(), strContent.data() + strContent.size(), &jvFileInfo, &errs))
{
LogWarn << "json parse fail content:" << strContent;
return false;
}
return true;
}
/**
* json格式内容写入文件
* inParam : Json::Value &jvFileInfo :json格式内容
: std::string &strFilePath :
* outParam: N/A
* return : true/false
*/
bool MyUtils::WriteJsonInfo(Json::Value &jvFileInfo, std::string &strFilePath)
{
Json::StreamWriterBuilder jswBuilder;
jswBuilder["indentation"] = "";
std::string strFrameInfo = Json::writeString(jswBuilder, jvFileInfo);
std::ofstream ofs(strFilePath.c_str());
if (!ofs.is_open())
{
LogWarn << "txt:" << strFilePath << " open fail";
return false;
}
ofs.write(strFrameInfo.c_str(), strFrameInfo.length());
ofs.close();
return true;
}
/**
* 1
* inParam : std::vector<stDetection> &vecResult
* outParam: std::vector<stDetection> &vecResult
* return : N/A
*/
void MyUtils::GetMaxScoreResult(std::vector<stDetection> &vecResult)
{
if (vecResult.size() < 2)
{
return;
}
std::map<Target, std::vector<stDetection>> mapResult;
for (size_t i = 0; i < vecResult.size(); i++)
{
stDetection stDTemp = vecResult.at(i);
if (stDTemp.class_id == 0)
{
mapResult[HEAD].emplace_back(stDTemp);
}
else if (stDTemp.class_id == 1)
{
mapResult[PRO].emplace_back(stDTemp);
}
else if ((stDTemp.class_id >= 2 && stDTemp.class_id <= 6) || stDTemp.class_id == 8 || stDTemp.class_id == 15)
{
mapResult[NUM].emplace_back(stDTemp);
}
else if (stDTemp.class_id >= 9 && stDTemp.class_id <= 17 && stDTemp.class_id != 15)
{
mapResult[TRAINSPACE].emplace_back(stDTemp);
}
else if (stDTemp.class_id == 18)
{
mapResult[SPACE].emplace_back(stDTemp);
}
}
//清空之前的结果
vecResult.clear();
// 每个类别中,获取得分最高的框
for (auto iter = mapResult.begin(); iter != mapResult.end(); iter++)
{
int iMaxPos = -1;
for (size_t i = 0; i < iter->second.size(); i++)
{
if (iMaxPos == -1)
{
iMaxPos = i;
}
else if (iter->second.at(i).class_conf > iter->second.at(iMaxPos).class_conf)
{
iMaxPos = i;
}
}
if (iMaxPos >= 0)
{
vecResult.emplace_back(iter->second.at(iMaxPos));
}
}
}
/**
*
* inParam : Step1Location &step1Location
: int iModelWidth
: int iModelHeight
* outParam: N/A
* return :
*/
float MyUtils::GetStep2ResizeRatio(Step1Location &step1Location, int iModelWidth, int iModelHeight)
{
uint32_t iCropgWidth = step1Location.fRBX - step1Location.fLTX;
uint32_t iCropHeight = step1Location.fRBY - step1Location.fLTY;
float fRatioW = static_cast<float>(iCropgWidth) / iModelWidth;
float fRatioH = static_cast<float>(iCropHeight) / iModelHeight;
return (fRatioW > fRatioH) ? fRatioW : fRatioH;
}
/**
*
* inParam : SingleData &singleData
: float fResizeRatio
: std::shared_ptr<ProcessData> pProcessData
: Step1Location &step1Location
* outParam: SingleData &singleData
* return : N/A
*/
void MyUtils::Step2ResetLocation(SingleData &singleData, float fResizeRatio,
std::shared_ptr<ProcessData> pProcessData, Step1Location &step1Location)
{
uint32_t iOrigWidth = pProcessData->iWidth;
uint32_t iOrigHeight = pProcessData->iHeight;
singleData.fLTX = singleData.fLTX * fResizeRatio + step1Location.fLTX;
singleData.fLTY = singleData.fLTY * fResizeRatio + step1Location.fLTY;
singleData.fRBX = singleData.fRBX * fResizeRatio + step1Location.fLTX;
singleData.fRBY = singleData.fRBY * fResizeRatio + step1Location.fLTY;
singleData.fLTX = (singleData.fLTX < iOrigWidth) ? singleData.fLTX : iOrigWidth;
singleData.fLTY = (singleData.fLTY < iOrigHeight) ? singleData.fLTY : iOrigHeight;
singleData.fRBX = (singleData.fRBX < iOrigWidth) ? singleData.fRBX : iOrigWidth;
singleData.fRBY = (singleData.fRBY < iOrigHeight) ? singleData.fRBY : iOrigHeight;
}
}