File indexing completed on 2025-08-05 08:09:42
0001
0002
0003
0004
0005
0006
0007
0008
0009 #include "Acts/Vertexing/FsmwMode1dFinder.hpp"
0010
0011 #include "Acts/Vertexing/VertexingError.hpp"
0012
0013 #include <algorithm>
0014 #include <cmath>
0015 #include <limits>
0016
0017 Acts::FsmwMode1dFinder::FsmwMode1dFinder(double firstFraction, double fraction)
0018 : m_firstFraction(firstFraction), m_fraction(fraction) {}
0019
0020 Acts::Result<double> Acts::FsmwMode1dFinder::getMode(
0021 std::vector<std::pair<double, double>> inputVector) const {
0022 if (inputVector.empty()) {
0023 return VertexingError::EmptyInput;
0024 }
0025 if (inputVector.size() == 1) {
0026 return inputVector.begin()->first;
0027 }
0028
0029
0030
0031 std::sort(inputVector.begin(), inputVector.end(),
0032 [](std::pair<double, double> a, std::pair<double, double> b) {
0033 return a.first < b.first;
0034 });
0035
0036
0037 auto begin = inputVector.begin();
0038 auto end = inputVector.end();
0039
0040 double overallweight(0.);
0041 auto best_begin = begin;
0042 auto best_end = end;
0043
0044 double last_value = std::numeric_limits<double>::max();
0045
0046 bool isthelast = false;
0047
0048 int counter = 0;
0049 double fraction = m_firstFraction;
0050 while (!isthelast) {
0051 counter += 1;
0052 if (counter == 2) {
0053 fraction = m_fraction;
0054 }
0055 int step = (int)std::floor(fraction * (end - begin + 1));
0056 overallweight = 0.;
0057 {
0058 auto i = begin;
0059 if (step > 0) {
0060 auto j_end = i + step - 1;
0061 for (auto j = i; j != j_end; j++) {
0062 overallweight += j->second;
0063 }
0064 }
0065 }
0066 auto i_last = begin + step - 1;
0067
0068 for (auto i = begin; i != (end - step + 1); ++i, ++i_last) {
0069
0070 overallweight += i_last->second;
0071
0072 double new_value = ((i + step - 1)->first - i->first) / overallweight;
0073 if (new_value < last_value) {
0074 last_value = ((i + step - 1)->first - i->first) / overallweight;
0075 best_begin = i;
0076 best_end = i + step - 1;
0077 }
0078 overallweight -= i->second;
0079 }
0080
0081
0082 begin = best_begin;
0083 end = best_end;
0084 last_value = std::numeric_limits<double>::max();
0085
0086
0087 if (best_end - best_begin <= 2) {
0088 isthelast = true;
0089 }
0090 }
0091
0092 if (best_end - best_begin == 2) {
0093 auto medium = begin;
0094 medium++;
0095 return (begin->first * begin->second + medium->first * medium->second +
0096 end->first * end->second) /
0097 (begin->second + medium->second + end->second);
0098 }
0099
0100 return (begin->first * begin->second + end->first * end->second) /
0101 (begin->second + end->second);
0102 }