Digitalisierte Elektroverteilung zur permanenten Verbraucherüberwachung
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

MLLinReg.cpp 2.8KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374
  1. #include "MLLinReg.h"
  2. #include "SystemConfig.h"
  3. #include <easylogging++.h>
  4. #include <fstream>
  5. #include <iomanip>
  6. MLLinReg::MLLinReg(CappedStorage *storage) : MLAnalyzer(storage)
  7. {
  8. criticalResidualCurrent = SystemConfig::getFloatConfigParameter("crit_residual_current");
  9. criticalTimeRangeSec = SystemConfig::getIntConfigParameter("crit_residual_timerange") * SECONDS_IN_WEEK;
  10. Theta.resize(2, 1);
  11. }
  12. MLAlert MLLinReg::updateModel()
  13. {
  14. if(t0 == 0 && data->getX().rows() != 0) {LOG(INFO) << std::setprecision(12) << std::fixed << "t_0 = " << (data->getX())(0, 1); t0 = (data->getX())(0, 1);}
  15. if(++updateCounter < updateRate)
  16. return MLAlert(CustomAlertTypes::NO_ALERT, "");
  17. updateCounter = 0;
  18. LOG(INFO) << "Update Linear Regression Model";
  19. normalEquation();
  20. bool error = checkCritical();
  21. if(error){
  22. //Return an alert object if tendency is critical
  23. std::stringstream ans;
  24. ans << "Received critical tendency in the next " << std::round(criticalTimeRangeSec/SECONDS_IN_WEEK) << " seconds";
  25. //LOG(INFO) << "Theta values: " << Theta(0) << " " << Theta(1);
  26. //if(first){
  27. // std::ofstream file;
  28. // std::stringstream ss;
  29. // file.open("debug_lin_reg.txt", std::ios::out);
  30. // if(file.is_open()){
  31. // file << std::setprecision(12) << std::fixed << "Theta: " << Theta(0) << " " << Theta(1) << std::endl;
  32. // file << std::setprecision(12) << std::fixed << "X: " << data->getX()(data->getX().rows()-1, 1) << std::endl;
  33. // file << std::setprecision(12) << std::fixed << "y: " << data->getY()(data->getY().rows()-1) << std::endl;
  34. // file << std::setprecision(12) << std::fixed << "t0: " << t0 << std::endl;
  35. // file << std::setprecision(12) << std::fixed << std::endl;
  36. // file.close();
  37. // }
  38. // first = false;
  39. //}
  40. return MLAlert(CustomAlertTypes::CRIT_RCM_TENDENCY, ans.str());
  41. }
  42. else
  43. return MLAlert(CustomAlertTypes::NO_ALERT, "");
  44. }
  45. bool MLLinReg::checkCritical(){
  46. //Check, if the critical value is reached within the specified time range
  47. if(data->getM() == 0)
  48. return false;
  49. //Offset, to avoid checking with little data and receive faulty results
  50. if(data->getM() < 100)
  51. return false;
  52. return (Theta(0) + Theta(1) * ((data->getX())((data->getX()).rows()-1, 1) + criticalTimeRangeSec))
  53. >= criticalResidualCurrent;
  54. }
  55. //Numerical approach to solve univariate Linear Regression Model
  56. void MLLinReg::normalEquation() {
  57. Theta = Eigen::MatrixXd::Zero(2, 1);
  58. Theta = (data->getX().transpose() * data->getX()).inverse() * data->getX().transpose() * data->getY();
  59. if(data->getX().rows() > 500){
  60. LOG(INFO) << Theta(0) << " " << Theta(1);
  61. LOG(INFO) << data->getX().rows();
  62. }
  63. }