409 lines
15 KiB
C++
409 lines
15 KiB
C++
#include <eqpm/eqpm_alg.h>
|
||
#include <eqpm/table_struct/fv_pdi.h>
|
||
#include <eqpm/table_struct/t_eqp_data.h>
|
||
#include <eqpm/table_struct/t_eqp_repair.h>
|
||
#include <mix_cc/sql.h>
|
||
#include <mix_cc/sql/database/db2_t.h>
|
||
#include <limits>
|
||
EqpmAlg::EqpmAlg() {
|
||
logger_ = std::make_unique<LOG>("EqpmAlg");
|
||
init_time_ = mix_cc::mix_time_t("2024-01-01 00:00:00")
|
||
.to_chrono_time(); ///<默认初始时间
|
||
}
|
||
EqpmAlg::~EqpmAlg() { logger_->Debug() << "EqpmAlg::~EqpmAlg()" << endl; }
|
||
void EqpmAlg::update_repair() {
|
||
logger_->Debug() << "EqpmAlg::update_repair()" << endl;
|
||
this->update_data();
|
||
this->select_repair();
|
||
if (!map_rules_.empty()) {
|
||
for (auto item : map_rules_) {
|
||
if (this->select_eqp_data(item.first) == 0) {
|
||
logger_->Debug() << "eqpid:" << item.first << ",rule_type"
|
||
<< map_rules_[item.first].rule_type << ",repair_date:"
|
||
<< mix_cc::mix_time_t(
|
||
map_rules_[item.first].repair_date)
|
||
.to_formatted_time()
|
||
<< ",interval:" << map_rules_[item.first].data << endl;
|
||
auto res = update_rule_data(
|
||
item.first, map_rules_[item.first].rule_type,
|
||
map_rules_[item.first].repair_date, map_rules_[item.first].data);
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
int EqpmAlg::init() {
|
||
// std::lock_guard<std::mutex> guard(local_mutext);
|
||
if (EqpmShm::TimeRecordPtr.get()->stime < EqpmShm::MinTime ||
|
||
EqpmShm::TimeRecordPtr.get()->stime >=
|
||
EqpmShm::TimeRecordPtr.get()->etime) {
|
||
EqpmShm::TimeRecordPtr.get()->stime = UtilityTools::time_point2second_zero(
|
||
chrono::system_clock::now() - std::chrono::days(EqpmShm::Defalt_Days));
|
||
EqpmShm::TimeRecordPtr.get()->etime = EqpmShm::TimeRecordPtr.get()->stime;
|
||
}
|
||
EqpmShm_stime_ =
|
||
UtilityTools::second_zero2time_point(EqpmShm::TimeRecordPtr.get()->stime);
|
||
this->update_data();
|
||
this->update_repair();
|
||
return 0;
|
||
}
|
||
|
||
bool EqpmAlg::update_data() {
|
||
// std::lock_guard<std::mutex> guard(local_mutext);
|
||
|
||
this->stime_ =
|
||
UtilityTools::second_zero2time_point(EqpmShm::TimeRecordPtr.get()->etime);
|
||
this->etime_ =
|
||
UtilityTools::time_point2zero(std::chrono::system_clock::now());
|
||
logger_->Debug() << "EqpmShm时间"
|
||
<< mix_cc::mix_time_t(EqpmShm_stime_).to_formatted_time()
|
||
<< "~"
|
||
<< mix_cc::mix_time_t(this->stime_).to_formatted_time()
|
||
<< ";EqpmShm数据量:" << EqpmShm::EqpmRecordPtr.get()->size()
|
||
<< endl;
|
||
|
||
if (this->etime_ - this->stime_ >= std::chrono::days(1)) {
|
||
for (TimePoint t1 = this->stime_; t1 < this->etime_;
|
||
t1 += std::chrono::days(1)) {
|
||
logger_->Debug() << "t1:" << mix_cc::mix_time_t(t1).to_formatted_time()
|
||
<< endl;
|
||
/*查 t1,t1+1天的数据,插入map index = (t1-内存中的stime)%最长保存时间*/
|
||
auto res = this->select_eqpm_data(t1); ///<刷新eqpm_record_
|
||
int index = this->get_index(t1);
|
||
EqpmShm::EqpmRecordPtr.get()->operator[](index) = eqpm_record_;
|
||
EqpmShm::TimeRecordPtr.get()->etime =
|
||
UtilityTools::time_point2second_zero(t1);
|
||
if (res) {
|
||
EqpmShm::TimeRecordPtr.get()->per_length = eqpm_record_.length;
|
||
EqpmShm::TimeRecordPtr.get()->per_weight = eqpm_record_.weight;
|
||
}
|
||
}
|
||
}
|
||
|
||
logger_->Debug() << "EqpmShm时间"
|
||
<< mix_cc::mix_time_t(EqpmShm_stime_).to_formatted_time()
|
||
<< "~"
|
||
<< mix_cc::mix_time_t(this->etime_).to_formatted_time()
|
||
<< ";EqpmShm数据量:" << EqpmShm::EqpmRecordPtr.get()->size()
|
||
<< endl;
|
||
update_slope(this->etime_ - std::chrono::days(1));
|
||
return true;
|
||
}
|
||
|
||
bool EqpmAlg::select_eqpm_data(TimePoint stime) {
|
||
eqpm_record_.length = 0;
|
||
eqpm_record_.weight = 0;
|
||
FV_PDI fp;
|
||
auto sql_statement =
|
||
select(fp.weight(), fp.length())
|
||
.from(fp)
|
||
.where(
|
||
fp.startime() > mix_cc::mix_time_t(stime),
|
||
fp.startime() < mix_cc::mix_time_t(stime + std::chrono::days(1)));
|
||
auto sample_list_maybe = exec<db2_t, FV_PDI>(sql_statement);
|
||
if (sample_list_maybe.is_just()) {
|
||
auto sample_list = sample_list_maybe.unsafe_get_just();
|
||
if (sample_list.empty()) {
|
||
logger_->Debug() << mix_cc::mix_time_t(stime).to_formatted_time() << "~"
|
||
<< mix_cc::mix_time_t(stime + std::chrono::days(1))
|
||
.to_formatted_time()
|
||
<< ":无数据!" << std::endl;
|
||
return false;
|
||
} else {
|
||
for (auto item : sample_list) {
|
||
eqpm_record_.length += item.length / 1000.0;
|
||
eqpm_record_.weight += item.weight / 1000.0;
|
||
}
|
||
}
|
||
} else {
|
||
logger_->Error() << "EqpmAlg::select_eqpm_data查询失败!" << std::endl;
|
||
return false;
|
||
}
|
||
return true;
|
||
}
|
||
|
||
int EqpmAlg::get_index(TimePoint time) {
|
||
return abs(UtilityTools::diff_days(EqpmShm_stime_, time) % (EqpmShm::Days));
|
||
}
|
||
|
||
int EqpmAlg::update_repair(std::string mq) {
|
||
try {
|
||
logger_->Debug() << "EqpmAlg::update_repair:" << mq << std::endl;
|
||
mix_cc::json js1 = mix_cc::json::parse(mq);
|
||
std::string eqpid = js1.at("eqpid").get<std::string>();
|
||
double interval = std::stod(js1.at("interval").get<std::string>());
|
||
int rule_type = js1.at("type").get<int>();
|
||
TimePoint repair_date =
|
||
UtilityTools::string2TimePoint(js1.at("repairdate").get<std::string>());
|
||
auto res = update_rule_data(eqpid, rule_type, repair_date, interval);
|
||
// js1.at("data") = rule_.data;
|
||
// js1.at("repairplan") =
|
||
// mix_cc::mix_time_t(rule_.repair_plan).to_formatted_time();
|
||
js1["data"] = rule_.data;
|
||
js1["repairplan"] =
|
||
mix_cc::mix_time_t(rule_.repair_plan).to_formatted_time();
|
||
std::string message = js1.dump();
|
||
logger_->Debug() << message << endl;
|
||
return res;
|
||
} catch (const std::exception& e) {
|
||
logger_->Error() << "EqpmAlg::update_repair,mq:" << mq
|
||
<< ",ERROR:" << e.what() << endl;
|
||
return -1;
|
||
}
|
||
}
|
||
|
||
int EqpmAlg::update_rule_data(std::string eqpid, int rule_type,
|
||
TimePoint repair_date, double interval) {
|
||
if (rule_type == 0) {
|
||
logger_->Info() << "eqpid:" << eqpid << ",无检修规则!" << endl;
|
||
return -1;
|
||
}
|
||
EqpRule eqpm_rule;
|
||
eqpm_rule.repair_date = UtilityTools::time_point2zero(repair_date);
|
||
eqpm_rule.rule_type = rule_type;
|
||
eqpm_rule.data = 0;
|
||
eqpm_rule.repair_plan = map_rules_[eqpid].repair_plan;
|
||
auto stime = eqpm_rule.repair_date;
|
||
auto etime = UtilityTools::time_point2zero(std::chrono::system_clock::now());
|
||
TimePoint target_time = etime; ///<检修时间
|
||
double data_before; ///<
|
||
bool is_miss = false;
|
||
switch (rule_type) {
|
||
case 0:
|
||
logger_->Debug() << eqpid << ":无规则!" << endl;
|
||
// return -1;
|
||
break;
|
||
case 3: {
|
||
/*时间 单位 天*/
|
||
eqpm_rule.data = UtilityTools::diff_days(
|
||
eqpm_rule.repair_date, std::chrono::system_clock::now());
|
||
|
||
int dist_days = int(interval - eqpm_rule.data);
|
||
if (dist_days > 365 * EqpmShm::MaxYear) {
|
||
dist_days = 365 * EqpmShm::MaxYear;
|
||
}
|
||
eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);
|
||
} break;
|
||
case 2: {
|
||
/*长度 单位 千米*/
|
||
for (TimePoint t1 = stime; t1 < etime; t1 += std::chrono::days(1)) {
|
||
int index = this->get_index(t1);
|
||
data_before = eqpm_rule.data;
|
||
eqpm_rule.data +=
|
||
EqpmShm::EqpmRecordPtr.get()->operator[](index).length;
|
||
if (data_before < interval && eqpm_rule.data >= interval) {
|
||
target_time = t1;
|
||
is_miss = true;
|
||
logger_->Debug()
|
||
<< "应该点检的时间:"
|
||
<< mix_cc::mix_time_t(target_time).to_formatted_time() << endl;
|
||
}
|
||
}
|
||
int dist_days = (interval - eqpm_rule.data) / this->length_slope_;
|
||
if (dist_days > 365 * EqpmShm::MaxYear) {
|
||
dist_days = 365 * EqpmShm::MaxYear;
|
||
}
|
||
eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);
|
||
if (is_miss) {
|
||
eqpm_rule.repair_plan = target_time;
|
||
}
|
||
// int dist_days = (interval - eqpm_rule.data) / this->length_slope_;
|
||
// if (dist_days > 365 * EqpmShm::MaxYear) {
|
||
// dist_days = 365 * EqpmShm::MaxYear;
|
||
// }
|
||
|
||
// if (dist_days >= 0) {
|
||
// eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);
|
||
// } else {
|
||
// // if (interval < this->length_slope_) {
|
||
// // eqpm_rule.repair_plan = repair_date + std::chrono::days(1);
|
||
// // }
|
||
// eqpm_rule.repair_plan = target_time;
|
||
// if (eqpm_rule.repair_plan < this->init_time_) {
|
||
// eqpm_rule.repair_plan = etime;
|
||
// }
|
||
// }
|
||
// eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);
|
||
// if (dist_days < 0) {
|
||
// eqpm_rule.repair_plan = etime;
|
||
// }
|
||
logger_->Debug()
|
||
<< eqpid << ",dist_days:" << dist_days << ",interval:" << interval
|
||
<< ",data:" << eqpm_rule.data << ",length_slope_:" << length_slope_
|
||
<< ",repair_date:"
|
||
<< mix_cc::mix_time_t(eqpm_rule.repair_date).to_formatted_time()
|
||
<< ",repair_plan:"
|
||
<< mix_cc::mix_time_t(eqpm_rule.repair_plan).to_formatted_time()
|
||
<< endl;
|
||
}
|
||
|
||
break;
|
||
case 1: {
|
||
/*重量 单位 吨*/
|
||
|
||
for (TimePoint t1 = stime; t1 < etime; t1 += std::chrono::days(1)) {
|
||
int index = this->get_index(t1);
|
||
data_before = eqpm_rule.data;
|
||
eqpm_rule.data +=
|
||
EqpmShm::EqpmRecordPtr.get()->operator[](index).weight;
|
||
if (data_before < interval && eqpm_rule.data >= interval) {
|
||
target_time = t1;
|
||
is_miss = true;
|
||
logger_->Debug()
|
||
<< "应该点检的时间:"
|
||
<< mix_cc::mix_time_t(target_time).to_formatted_time() << endl;
|
||
}
|
||
}
|
||
int dist_days = (interval - eqpm_rule.data) / this->weight_slope_;
|
||
if (dist_days > 365 * EqpmShm::MaxYear) {
|
||
dist_days = 365 * EqpmShm::MaxYear;
|
||
}
|
||
eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);
|
||
if (is_miss) {
|
||
eqpm_rule.repair_plan = target_time;
|
||
}
|
||
// int dist_days = (interval - eqpm_rule.data) / this->weight_slope_;
|
||
// if (dist_days > 365 * EqpmShm::MaxYear) {
|
||
// dist_days = 365 * EqpmShm::MaxYear;
|
||
// }
|
||
|
||
// if (dist_days >= 0) {
|
||
// eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);
|
||
// } else {
|
||
// // if (interval < this->length_slope_) {
|
||
// // eqpm_rule.repair_plan = repair_date + std::chrono::days(1);
|
||
// // }
|
||
// eqpm_rule.repair_plan = target_time;
|
||
// if (eqpm_rule.repair_plan < this->init_time_) {
|
||
// eqpm_rule.repair_plan = etime;
|
||
// }
|
||
// }
|
||
// eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);
|
||
// eqpm_rule.repair_plan = etime + std::chrono::days(dist_days);S
|
||
// if (dist_days < 0) {
|
||
// eqpm_rule.repair_plan = etime;
|
||
// }
|
||
logger_->Debug()
|
||
<< eqpid << ",dist_days:" << dist_days << ",interval:" << interval
|
||
<< ",data:" << eqpm_rule.data << ",weight_slope_:" << weight_slope_
|
||
<< ",repair_date:"
|
||
<< mix_cc::mix_time_t(eqpm_rule.repair_date).to_formatted_time()
|
||
<< ",repair_plan:"
|
||
<< mix_cc::mix_time_t(eqpm_rule.repair_plan).to_formatted_time()
|
||
<< endl;
|
||
} break;
|
||
default:
|
||
break;
|
||
}
|
||
// if (interval - eqpm_rule.data >= 0) {
|
||
// rule_ = eqpm_rule;
|
||
// return update_db2(eqpid);
|
||
// }
|
||
|
||
rule_ = eqpm_rule;
|
||
return update_db2(eqpid);
|
||
return -1;
|
||
}
|
||
|
||
int EqpmAlg::update_db2(std::string eqpid) {
|
||
T_EQP_REPAIR ter;
|
||
auto res = exec<db2_t, size_t>(
|
||
update(ter)
|
||
.set(ter.data() = rule_.data,
|
||
ter.repairplan() = mix_cc::mix_time_t(rule_.repair_plan))
|
||
.where(ter.eqpid() == eqpid));
|
||
if (!res.is_nothing()) {
|
||
auto res3 = res.unsafe_get_just();
|
||
if (res3 == 0) {
|
||
auto res2 = exec<db2_t, size_t>(insert_into(ter).set(
|
||
ter.eqpid() = eqpid, ter.data() = rule_.data,
|
||
ter.repairplan() = mix_cc::mix_time_t(rule_.repair_plan)));
|
||
if (res2.is_nothing()) {
|
||
logger_->Error() << "T_EQP_REPAIR,插入数据失败" << std::endl;
|
||
return -2;
|
||
}
|
||
}
|
||
|
||
} else {
|
||
logger_->Error() << "T_EQP_REPAIR,更新数据失败" << std::endl;
|
||
return -1;
|
||
}
|
||
return 0;
|
||
}
|
||
|
||
void EqpmAlg::update_slope(TimePoint date) {
|
||
double length = 0;
|
||
double weight = 0;
|
||
for (int i = 0; i < 3; i++) {
|
||
int index = this->get_index(date - std::chrono::days(i));
|
||
length += EqpmShm::EqpmRecordPtr.get()->operator[](index).length;
|
||
weight += EqpmShm::EqpmRecordPtr.get()->operator[](index).weight;
|
||
}
|
||
this->length_slope_ = length < std::numeric_limits<double>::epsilon()
|
||
? EqpmShm::TimeRecordPtr.get()->per_length
|
||
: length;
|
||
this->weight_slope_ = weight < std::numeric_limits<double>::epsilon()
|
||
? EqpmShm::TimeRecordPtr.get()->per_weight
|
||
: weight;
|
||
}
|
||
|
||
int EqpmAlg::select_repair() {
|
||
T_EQP_REPAIR ter;
|
||
auto sql_statement =
|
||
select(ter.eqpid(), ter.repairdate(), ter.repairplan()).from(ter);
|
||
auto sample_list_maybe = exec<db2_t, T_EQP_REPAIR>(sql_statement);
|
||
if (sample_list_maybe.is_just()) {
|
||
auto sample_list = sample_list_maybe.unsafe_get_just();
|
||
if (sample_list.empty()) {
|
||
logger_->Debug() << "T_EQP_REPAIR 无数据!" << std::endl;
|
||
return -2;
|
||
} else {
|
||
map_rules_.clear();
|
||
for (auto item : sample_list) {
|
||
map_rules_[item.eqpid].repair_date =
|
||
mix_cc::mix_time_t(item.repairdate).to_chrono_time();
|
||
map_rules_[item.eqpid].repair_plan =
|
||
mix_cc::mix_time_t(item.repairplan).to_chrono_time();
|
||
// if (mix_cc::mix_time_t(item.repairplan).to_chrono_time() !=
|
||
// this->init_time_) {
|
||
// map_rules_[item.eqpid].repair_plan =
|
||
// mix_cc::mix_time_t(item.repairplan).to_chrono_time();
|
||
// logger_->Debug()
|
||
// << item.eqpid << ","
|
||
// << "repairplan:"
|
||
// << mix_cc::mix_time_t(item.repairplan).to_formatted_time()
|
||
// << endl;
|
||
// }
|
||
}
|
||
logger_->Debug() << "规则数:" << map_rules_.size() << endl;
|
||
}
|
||
} else {
|
||
logger_->Error() << "EqpmAlg::select_repair()查询失败!" << std::endl;
|
||
return -1;
|
||
}
|
||
return 0;
|
||
}
|
||
|
||
int EqpmAlg::select_eqp_data(std::string eqpid) {
|
||
T_EQP_DATA ted;
|
||
auto sql_statement = select(ted.ruletype(), ted.value())
|
||
.from(ted)
|
||
.where(ted.ruletype() > 0, ted.eqpId() == eqpid);
|
||
auto sample_list_maybe = exec<db2_t, T_EQP_DATA>(sql_statement);
|
||
if (sample_list_maybe.is_just()) {
|
||
auto sample_list = sample_list_maybe.unsafe_get_just();
|
||
if (sample_list.empty()) {
|
||
logger_->Debug() << "T_EQP_DATA 无数据或无规则!" << std::endl;
|
||
return -2;
|
||
} else {
|
||
map_rules_[eqpid].data = sample_list[0].value;
|
||
map_rules_[eqpid].rule_type = sample_list[0].ruletype;
|
||
logger_->Debug() << eqpid << ",ruletype:" << map_rules_[eqpid].rule_type
|
||
<< ",value:" << map_rules_[eqpid].data << endl;
|
||
}
|
||
} else {
|
||
logger_->Error() << "EqpmAlg::select_repair()查询失败!" << std::endl;
|
||
return -1;
|
||
}
|
||
return 0;
|
||
} |