MatterElementAnalysis.cpp 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106
  1. //
  2. // Created by Austin on 2023/10/11.
  3. //
  4. #include "MatterElementAnalysis.h"
  5. MatterElementAnalysis::MatterElementAnalysis(const MEAMat &mat, const MEARangeMat &ranges) : mat_(mat), ranges_(ranges)
  6. {
  7. sample_num_ = mat_.count();
  8. if (sample_num_ == 0) {
  9. index_num_ = 0;
  10. } else {
  11. index_num_ = mat_.at(0).count();
  12. }
  13. for (int i = 0; i < sample_num_; ++i) {
  14. MEAMat cvtMat;
  15. for (int j = 0; j < index_num_; ++j) {
  16. cvtMat.append(QVector<double>(ranges_.count() - 1, 0.0));
  17. }
  18. range_cvt_.append(cvtMat);
  19. }
  20. for (int i = 0; i < sample_num_; ++i) {
  21. range_weights_.append(QVector<double>(ranges_.count() - 1, 0.0));
  22. }
  23. }
  24. void MatterElementAnalysis::evaluate(const QVector<double> &weights)
  25. {
  26. // 根据关联函数更新转换矩阵
  27. for (int s = 0; s < sample_num_; ++s) {
  28. for (int i = 0; i < index_num_; ++i) {
  29. double val = mat_.at(s).at(i);
  30. associatedValue(s, i, val);
  31. }
  32. }
  33. // QVector<double> weights_ = { 0.189, 0.203, 0.052, 0.162, 0.202, 0.151, 0.041 };
  34. evaluationlevel(weights);
  35. }
  36. void MatterElementAnalysis::associatedValue(int sam, int index, double value)
  37. {
  38. auto pFunc = [](double v, double left, double right) {
  39. return std::abs(v - (left + right) / 2) - (right - left) / 2;
  40. };
  41. double r = 0;
  42. for (int i = 0; i < ranges_.count() - 1; ++i) // i是等级,index是指标
  43. {
  44. Q_ASSERT(ranges_.at(i).at(index).index == index);
  45. double minValue = ranges_.at(i).at(index).min_value;
  46. double maxValue = ranges_.at(i).at(index).max_value;
  47. double minend = ranges_.last().at(index).min_value;
  48. double maxend = ranges_.last().at(index).max_value;
  49. double r1 = pFunc(value, minValue, maxValue);
  50. double r2 = pFunc(value, minend, maxend);
  51. if (abs(r1 - r2) <= 0.00000001) {
  52. r = -r1 - 1;
  53. } else {
  54. r = r1 / (r2 - r1);
  55. }
  56. range_cvt_[sam][index][i] = r;
  57. // 结果放在range_cvt_
  58. }
  59. }
  60. void MatterElementAnalysis::evaluationlevel(const QVector<double> &weights)
  61. { // 输入计算出来的关联度,权值
  62. // 计算一个样本权值之后的总关联度
  63. double r;
  64. for (int i = 0; i < sample_num_; ++i) // 样本
  65. for (int j = 0; j < ranges_.count() - 1; ++j) { // 等级
  66. r = 0;
  67. for (int k = 0; k < index_num_; ++k) { // 指标
  68. r = r + range_cvt_[i][k][j] * weights[k];
  69. }
  70. range_weights_[i][j] = r;
  71. }
  72. }
  73. const MEAMat &MatterElementAnalysis::getRangeWeights() const
  74. {
  75. return range_weights_;
  76. }
  77. QVector<int> MatterElementAnalysis::getBestIndex() const
  78. {
  79. auto maxLoc = [](const QVector<double> &v) {
  80. int index = 0;
  81. double maxValue = v.at(0);
  82. for (int i = 1; i < v.count(); ++i) {
  83. if (v.at(i) > maxValue) {
  84. maxValue = v.at(i);
  85. index = i;
  86. }
  87. }
  88. return index;
  89. };
  90. QVector<int> result;
  91. for (const auto &s : range_weights_) {
  92. result << maxLoc(s) + 1;
  93. }
  94. return result;
  95. }