15 #ifndef CLUSTERINGHELPER_H 
   16 #define CLUSTERINGHELPER_H 
   35   Cluster(
const std::vector<double> &
v, 
const std::vector<double> &v_sigma);
 
   37   Cluster(
const std::vector<double> &
v, 
const std::vector<double> &v_sigma,
 
   73                        const std::vector<double> &v_sigma);
 
   83   const std::vector<double>& 
getSigmas() 
const;
 
  147   const std::vector<Cluster<T>>& 
getClusters() 
const;
 
  173     : m_combined_value(-999.), m_combined_sigma(-999.) {}
 
  175 template <
typename T>
 
  177   const std::vector<double> &
v, 
const std::vector<double> &v_sigma)
 
  178   : m_combined_value_vector(
v), m_combined_sigma_vector(v_sigma) {
 
  180   for (
const auto &
s : v_sigma) {
 
  187 template <
typename T>
 
  189   const std::vector<double> &
v, 
const std::vector<double> &v_sigma,
 
  191   : m_combined_value_vector(
v), m_combined_sigma_vector(v_sigma) {
 
  195   for (
const auto &
s : v_sigma) {
 
  203   return m_entries.size();
 
  207   m_entries.push_back(
entry);
 
  216   if (not entry_vector.empty()) {
 
  217     m_entries.insert(m_entries.end(), entry_vector.begin(), entry_vector.end());
 
  223                                  const std::vector<double> &v_sigma) {
 
  224   m_combined_value_vector = 
v;
 
  225   m_combined_sigma_vector = v_sigma;
 
  230   if (m_combined_value_vector.size() == 0) {
 
  231     if (m_debug_level > 0) {
 
  233           << 
"Cluster::getTime: ATTENTION, combi values are not initialized!" 
  237   return m_combined_value_vector;
 
  241   return m_combined_sigma_vector;
 
  251   return m_merge_iteration;
 
  255   m_merge_iteration = iteration;
 
  259   return m_contains_unknowns;
 
  263   m_contains_unknowns = 
status;
 
  271   m_distance_cut = cut_value;
 
  275   m_clusters.push_back(vx);
 
  278 template <
typename T>
 
  281   std::vector<double> a_values = 
a.getValues();
 
  282   std::vector<double> b_values = 
b.getValues();
 
  283   std::vector<double> a_sigmas = 
a.getSigmas();
 
  284   std::vector<double> b_sigmas = 
b.getSigmas();
 
  286   std::vector<double> distances(a_values.size());
 
  287   for (
size_t i = 0; 
i < a_values.size(); 
i++) {
 
  288     double distance_i = 0;
 
  289     if (a_sigmas.at(
i) >= 0.0 && b_sigmas.at(
i) >= 0.0) {
 
  290       distance_i = std::abs(a_values.at(
i) - b_values.at(
i)) /
 
  291                    std::hypot(a_sigmas.at(
i), b_sigmas.at(
i));
 
  293     distances.at(
i) = distance_i;
 
  296   for (
double d : distances) {
 
  309   std::vector<double> a_values = 
a.getValues();
 
  310   std::vector<double> b_values = 
b.getValues();
 
  311   std::vector<double> a_sigmas = 
a.getSigmas();
 
  312   std::vector<double> b_sigmas = 
b.getSigmas();
 
  314   std::vector<double> new_cluster_values(a_values.size());
 
  315   std::vector<double> new_cluster_sigmas(a_values.size());
 
  317   for (
size_t i = 0; 
i < a_values.size(); 
i++) {
 
  318     double value1 = a_values.at(
i);
 
  319     double value2 = b_values.at(
i);
 
  320     double var1 = 
std::pow(a_sigmas.at(
i), 2.0);
 
  321     double var2 = 
std::pow(b_sigmas.at(
i), 2.0);
 
  322     double new_cluster_value =
 
  323         (value1 / var1 + 
value2 / var2) / (1.0 / var1 + 1.0 / var2);
 
  324     double new_cluster_sigma = std::sqrt(var1 * var2 / (var1 + var2));
 
  325     new_cluster_values.at(
i) = new_cluster_value;
 
  326     new_cluster_sigmas.at(
i) = new_cluster_sigma;
 
  328   int new_merge_iteration = 
a.getMergeIteration() + 
b.getMergeIteration() + 1;
 
  329   merged_cluster.
setClusterValue(new_cluster_values, new_cluster_sigmas);
 
  332   return merged_cluster;
 
  342   std::vector<double> a_values = 
a.getValues();
 
  343   std::vector<double> b_values = 
b.getValues();
 
  344   std::vector<double> a_sigmas = 
a.getSigmas();
 
  345   std::vector<double> b_sigmas = 
b.getSigmas();
 
  347   std::vector<double> new_cluster_values(a_values.size());
 
  348   std::vector<double> new_cluster_sigmas(a_values.size());
 
  350   for (
size_t i = 0; 
i < a_values.size(); 
i++) {
 
  351     double value1 = a_values.at(
i);
 
  352     double value2 = b_values.at(
i);
 
  353     double sigma1 = a_sigmas.at(
i);
 
  354     double sigma2 = b_sigmas.at(
i);
 
  355     double new_cluster_value = (value1 + 
value2) / 2.;
 
  356     double new_cluster_sigma = std::hypot(sigma1, sigma2);
 
  357     new_cluster_values.at(
i) = new_cluster_value;
 
  358     new_cluster_sigmas.at(
i) = new_cluster_sigma;
 
  360   int new_merge_iteration = 
a.getMergeIteration() + 
b.getMergeIteration() + 1;
 
  361   merged_cluster.
setClusterValue(new_cluster_values, new_cluster_sigmas);
 
  364   return merged_cluster;
 
  367 template <
typename T>
 
  370     for (
const auto &clust : m_clusters) {
 
  371       if (clust.containsUnknowns()) {
 
  372         throw std::invalid_argument(
 
  373             "[ClusterCollection::doClustering] ERROR " 
  374             "- eager clustering does not allow for unknown values");
 
  380   if (m_debug_level > 0) {
 
  381     std::cout << 
"ClusterCollection::doTimeClustering" << std::endl;
 
  385   while (m_clusters.size() > 1) {
 
  388     if (m_debug_level > 0) {
 
  389       std::cout << 
"using " << m_clusters.size() << 
" vertices" << std::endl;
 
  392     distance = getDistanceBetweenClusters(m_clusters.at(0), m_clusters.at(1));
 
  393     for (
size_t i = 0; 
i < m_clusters.size(); 
i++) {
 
  394       for (
size_t j = 
i + 1; j < m_clusters.size(); j++) {
 
  399           if (m_clusters.at(
i).mergeStatus() or m_clusters.at(j).mergeStatus()) {
 
  404         double current_distance =
 
  405             getDistanceBetweenClusters(m_clusters.at(
i), m_clusters.at(j));
 
  413     if (m_debug_level > 0) {
 
  414       std::cout << 
"using vertex " << i0 << 
" and " << j0 << std::endl;
 
  417     if (
distance < m_distance_cut && i0 != j0) {
 
  422         new_cluster = mergeClustersMean(m_clusters.at(i0), m_clusters.at(j0));
 
  424         new_cluster = mergeClusters(m_clusters.at(i0), m_clusters.at(j0));
 
  427       if (m_debug_level > 0) {
 
  428         std::cout << 
"starting to erase" << std::endl;
 
  430       m_clusters.erase(m_clusters.begin() + j0);
 
  432         m_clusters.erase(m_clusters.begin() + i0);
 
  434         m_clusters.erase(m_clusters.begin() + (i0 - 1));
 
  436       if (m_debug_level > 0) {
 
  437         std::cout << 
"erase done" << std::endl;
 
  439       m_clusters.push_back(new_cluster);
 
  440       if (m_debug_level > 0) {
 
  441         std::cout << 
"new cluster stored" << std::endl;
 
  448       if (std::find_if(m_clusters.begin(), m_clusters.end(),
 
  449                        [](
const Cluster<T> &
c) { return c.mergeStatus(); }) !=
 
  452         std::for_each(m_clusters.begin(), m_clusters.end(), [](
Cluster<T> &
c) {
 
  453           c.setMergeStatus(false);
 
  463 template <
typename T>
 
  470   for (
const auto& vx : m_clusters) {
 
  473     if (current_n > max_n_hits) {
 
  474       max_n_hits = current_n;
 
  478     else if (current_n == max_n_hits) {
 
  483   return std::make_pair(max_n_vertex, 
count);
 
  488   const auto [max_cluster, nMaxClusters] = largestClusterInfo();
 
  491   if (nMaxClusters > 1) {
 
  500   const auto [max_cluster, nMaxClusters] = largestClusterInfo();
 
  502   return max_cluster.getNEntries();
 
  505 template <
typename T>
 
  511   return static_cast<int>(m_clusters.size());
 
  516 #endif // CLUSTERINGHELPER_H