25 std::vector<DiagramType> &final_centroids,
26 std::vector<std::vector<std::vector<std::vector<MatchingType>>>>
27 &all_matchings_per_type_and_cluster) {
29 all_matchings_per_type_and_cluster.resize(
k_);
30 for(
int c = 0; c <
k_; c++) {
31 all_matchings_per_type_and_cluster[c].resize(3);
32 for(
int i = 0; i < 3; i++) {
36 int matchings_only =
false;
46 matchings_only =
true;
51 std::vector<bool *> current_prec;
56 std::vector<bool *> current_dos;
57 current_dos.emplace_back(&
do_min_);
58 current_dos.emplace_back(&
do_sad_);
59 current_dos.emplace_back(&
do_max_);
60 bool converged =
false;
61 std::vector<bool> diagrams_complete(3);
62 for(
int c = 0; c < 3; c++) {
66 double total_time = 0;
70 cost_ = std::numeric_limits<double>::max();
71 double min_cost_min = std::numeric_limits<double>::max();
72 double min_cost_max = std::numeric_limits<double>::max();
73 double min_cost_sad = std::numeric_limits<double>::max();
75 double last_min_cost_obtained_min = -1;
76 double last_min_cost_obtained_sad = -1;
77 double last_min_cost_obtained_max = -1;
78 std::vector<double> epsilon0(3);
79 std::vector<double> epsilon_candidate(3);
80 std::vector<double> rho(3);
83 std::vector<double> max_persistence(3);
84 std::vector<double> lowest_persistence(3);
85 std::vector<double> min_persistence(3);
87 const auto square = [](
const double a) {
return a * a; };
89 for(
int i_crit = 0; i_crit < 3; i_crit++) {
92 min_persistence[i_crit] = 0;
93 epsilon_[i_crit] = square(0.5 * max_persistence[i_crit])
99 std::vector<int> min_points_to_add(3);
100 min_points_to_add[0] = 10;
101 min_points_to_add[1] = 10;
102 min_points_to_add[2] = 10;
106 min_points_to_add[0] = std::numeric_limits<int>::max();
107 min_points_to_add[1] = std::numeric_limits<int>::max();
108 min_points_to_add[2] = std::numeric_limits<int>::max();
110 std::vector<std::vector<double>> min_diag_price(3);
111 std::vector<std::vector<double>> min_off_diag_price(3);
112 for(
int c = 0; c < 3; ++c) {
114 min_diag_price[c].emplace_back(0);
115 min_off_diag_price[c].emplace_back(0);
119 max_persistence, min_persistence, min_diag_price, min_off_diag_price,
120 min_points_to_add,
false,
true);
122 for(
int c = 0; c < 3; c++) {
123 if(min_persistence[c] <= lowest_persistence[c]) {
124 diagrams_complete[c] =
true;
127 bool all_diagrams_complete
128 = diagrams_complete[0] && diagrams_complete[1] && diagrams_complete[2];
129 if(all_diagrams_complete) {
158 for(
int i_crit = 0; i_crit < 3; i_crit++) {
159 if(*(current_dos[i_crit])) {
160 rho[i_crit] = min_persistence[i_crit] > 0
172 for(
int i_crit = 0; i_crit < 3; i_crit++) {
173 if(*(current_dos[i_crit])) {
174 epsilon_candidate[i_crit] = square(min_persistence[i_crit]) / 8.;
175 if(epsilon_candidate[i_crit] >
epsilon_[i_crit]) {
178 epsilon_[i_crit] = epsilon_candidate[i_crit];
186 min_persistence[0] = 0;
187 min_points_to_add[0] = std::numeric_limits<int>::max();
192 min_persistence[1] = 0;
193 min_points_to_add[1] = std::numeric_limits<int>::max();
198 min_persistence[2] = 0;
199 min_points_to_add[2] = std::numeric_limits<int>::max();
204 min_persistence, rho, min_diag_price, min_off_diag_price,
205 min_points_to_add,
true,
false);
209 for(
int i_crit = 0; i_crit < 3; i_crit++) {
210 if(*(current_dos[i_crit])) {
211 if(min_persistence[i_crit] <= lowest_persistence[i_crit]) {
212 diagrams_complete[i_crit] =
true;
217 if(diagrams_complete[0] && diagrams_complete[1]
218 && diagrams_complete[2]) {
220 all_diagrams_complete =
true;
226 &min_off_diag_price, &min_diag_price,
227 all_matchings_per_type_and_cluster, matchings_only);
238 for(
int i_crit = 0; i_crit < 3; i_crit++) {
239 if(*(current_dos[i_crit]) ) {
240 epsilon_candidate[i_crit] = std::min(
241 std::max(max_shift_vec[i_crit] / 8.,
epsilon_[i_crit] / 5.),
244 if((epsilon_candidate[i_crit] <
epsilon_[i_crit]
245 && !diagrams_complete[i_crit])
246 || diagrams_complete[i_crit]) {
247 epsilon_[i_crit] = epsilon_candidate[i_crit];
255 this->
printMsg(
"[min barycenter] epsilon under minimal value ",
259 diagrams_complete[0] =
true;
262 this->
printMsg(
"[sad barycenter] epsilon under minimal value ",
266 diagrams_complete[1] =
true;
269 this->
printWrn(
"[max barycenter] epsilon under minimal value ");
272 diagrams_complete[2] =
true;
275 if(diagrams_complete[0] && diagrams_complete[1]
276 && diagrams_complete[2]) {
278 all_diagrams_complete =
true;
291 +
" epsilon " + std::to_string(
epsilon_[0]) +
" "
295 this->
printMsg(
" complete " + std::to_string(diagrams_complete[0]) +
" "
296 + std::to_string(diagrams_complete[1]) +
" "
297 + std::to_string(diagrams_complete[2]),
309 && diagrams_complete[0] ) {
311 last_min_cost_obtained_min = 0;
313 last_min_cost_obtained_min += 1;
314 if(last_min_cost_obtained_min > 1) {
320 && diagrams_complete[1] ) {
322 last_min_cost_obtained_sad = 0;
324 last_min_cost_obtained_sad += 1;
325 if(last_min_cost_obtained_sad > 1 && diagrams_complete[1]) {
331 && diagrams_complete[2] ) {
333 last_min_cost_obtained_max = 0;
335 last_min_cost_obtained_max += 1;
336 if(last_min_cost_obtained_max > 1 && diagrams_complete[2]) {
345 converged = converged
347 && !
do_max_ && (precision_criterion_reached))
362 all_diagrams_complete =
true;
363 diagrams_complete[0] =
true;
364 diagrams_complete[1] =
true;
365 diagrams_complete[2] =
true;
370 <<
" == complete : " << all_diagrams_complete
372 <<
" , converged : " << converged << std::endl;
378 std::vector<std::vector<std::string>>
const rows{
379 {
" Min-saddle cost", std::to_string(
cost_min_)},
380 {
" Saddle-saddle cost", std::to_string(
cost_sad_)},
381 {
" Saddle-max cost", std::to_string(
cost_max_)},
382 {matchings_only ?
"Wasserstein Distance" :
"Final Cost",
393 this->
printMsg(
"Clustering result:");
406 final_centroids.resize(
k_);
408 for(
int c = 0; c <
k_; c++) {
418 for(
int c = 0; c <
k_; ++c) {
422 int const removeFirstPairMin
424 int addedFirstPairMax = 0;
425 int addedFirstPairMin = removeFirstPairMin;
435 addedFirstPairMax = 1;
443 addedFirstPairMin = 1;
447 for(
size_t i = addedFirstPairMin; i <
centroids_min_[c].size(); ++i) {
455 this->
printMsg(
"Found a abnormally high persistence in min diagram",
470 this->
printMsg(
"Found a abnormally high persistence in sad diagram",
477 for(
size_t i = addedFirstPairMax; i <
centroids_max_[c].size(); ++i) {
492 this->
printMsg(
"Found a abnormally high persistence in min diagram",
509 std::vector<std::vector<std::vector<std::vector<MatchingType>>>>
510 &previous_matchings) {
511 for(
int c = 0; c <
k_; c++) {
512 for(
size_t i = 0; i <
clustering_[c].size(); i++) {
516 std::vector<int> new_to_old_id(
521 new_to_old_id[new_id] = j;
525 std::vector<MatchingType> matchings_diagram_i;
526 for(
size_t j = 0; j < previous_matchings[c][0][i].size(); j++) {
528 int const new_id = std::get<0>(m);
529 if(new_id >= 0 && std::get<1>(m) >= 0) {
530 std::get<0>(m) = new_to_old_id[new_id];
531 matchings_diagram_i.emplace_back(m);
532 }
else if(std::get<1>(m)
535 matchings_diagram_i.emplace_back(m);
538 previous_matchings[c][0][i].resize(matchings_diagram_i.size());
539 previous_matchings[c][0][i] = matchings_diagram_i;
543 std::vector<int> new_to_old_id(
548 new_to_old_id[new_id] = j;
553 std::vector<MatchingType> matchings_diagram_i;
554 for(
size_t j = 0; j < previous_matchings[c][1][i].size(); j++) {
556 int const new_id = std::get<0>(m);
557 if(new_id >= 0 && std::get<1>(m) >= 0) {
558 int const old_id = new_to_old_id[new_id];
560 std::get<0>(m) = old_id;
561 matchings_diagram_i.emplace_back(m);
565 std::get<0>(m) = old_id;
566 matchings_diagram_i.emplace_back(m);
569 }
else if(std::get<1>(m)
572 matchings_diagram_i.emplace_back(m);
575 previous_matchings[c][1][i].resize(matchings_diagram_i.size());
576 previous_matchings[c][1][i] = matchings_diagram_i;
580 std::vector<int> new_to_old_id(
585 new_to_old_id[new_id] = j;
590 std::vector<MatchingType> matchings_diagram_i;
591 for(
size_t j = 0; j < previous_matchings[c][2][i].size(); j++) {
593 int const new_id = std::get<0>(m);
594 if(new_id >= 0 && std::get<1>(m) >= 0) {
595 int const old_id = new_to_old_id[new_id];
597 std::get<0>(m) = old_id;
598 matchings_diagram_i.emplace_back(m);
602 std::get<0>(m) = old_id;
603 matchings_diagram_i.emplace_back(m);
606 }
else if(std::get<1>(m)
609 matchings_diagram_i.emplace_back(m);
612 previous_matchings[c][2][i].resize(matchings_diagram_i.size());
613 previous_matchings[c][2][i] = matchings_diagram_i;
948 std::vector<int> indexes_clusters;
950 indexes_clusters.emplace_back(random_idx);
968 const auto square = [](
const double a) {
return a * a; };
970 while((
int)indexes_clusters.size() <
k_) {
975 double maximal_distance = 0;
976 int candidate_centroid = 0;
980 min_distance_to_centroid[i] = std::numeric_limits<double>::max();
981 if(std::find(indexes_clusters.begin(), indexes_clusters.end(), i)
982 != indexes_clusters.end()) {
984 min_distance_to_centroid[i] = 0;
987 for(
size_t j = 0; j < indexes_clusters.size(); ++j) {
1008 if(distance < min_distance_to_centroid[i]) {
1009 min_distance_to_centroid[i] = distance;
1013 probabilities[i] = square(min_distance_to_centroid[i]);
1017 if(
deterministic_ && min_distance_to_centroid[i] > maximal_distance) {
1018 maximal_distance = min_distance_to_centroid[i];
1019 candidate_centroid = i;
1023 std::random_device rd;
1024 std::mt19937 gen(rd());
1025 std::discrete_distribution<int> distribution(
1026 probabilities.begin(), probabilities.end());
1029 candidate_centroid = distribution(gen);
1032 indexes_clusters.emplace_back(candidate_centroid);
1482 std::vector<std::vector<double>> *min_price,
1483 std::vector<std::vector<double>> *min_diag_price,
1484 std::vector<std::vector<std::vector<std::vector<MatchingType>>>>
1485 &all_matchings_per_type_and_cluster,
1486 int only_matchings) {
1488 std::vector<double> max_shift_vector(3);
1489 max_shift_vector[0] = 0;
1490 max_shift_vector[1] = 0;
1491 max_shift_vector[2] = 0;
1492 double max_shift_c_min = 0;
1493 double max_shift_c_sad = 0;
1494 double max_shift_c_max = 0;
1495 double max_wasserstein_shift = 0;
1496 bool precision_min =
true;
1497 bool precision_sad =
true;
1498 bool precision_max =
true;
1513 for(
int c = 0; c <
k_; ++c) {
1515 std::vector<GoodDiagram> centroids_with_price_min,
1516 centroids_with_price_sad, centroids_with_price_max;
1521 std::vector<int>::iterator
const i = std::find(
1529 centroids_with_price_min.emplace_back(
1533 centroids_with_price_sad.emplace_back(
1537 centroids_with_price_max.emplace_back(
1541 int number_of_points_min = 0;
1542 int number_of_points_max = 0;
1543 int number_of_points_sad = 0;
1548 centroids_with_price_min.emplace_back(
1556 centroids_with_price_sad.emplace_back(
1560 number_of_points_sad
1565 centroids_with_price_max.emplace_back(
1584 double estimated_delta_lim
1586 / sqrt(1 - number_of_points_min *
epsilon_[0] / sq_dist_min)
1588 if(estimated_delta_lim > 1) {
1589 estimated_delta_lim = 1;
1592 &(centroids_with_price_min[count]),
1593 estimated_delta_lim);
1598 double estimated_delta_lim
1600 / sqrt(1 - number_of_points_sad *
epsilon_[1] / sq_dist_sad)
1602 if(estimated_delta_lim > 1) {
1603 estimated_delta_lim = 1;
1606 &(centroids_with_price_sad[count]),
1607 estimated_delta_lim);
1612 double estimated_delta_lim
1614 / sqrt(1 - number_of_points_max *
epsilon_[2] / sq_dist_max)
1616 if(estimated_delta_lim > 1) {
1617 estimated_delta_lim = 1;
1620 &(centroids_with_price_max[count]),
1621 estimated_delta_lim);
1627 double total_cost = 0;
1628 double wasserstein_shift = 0;
1633 std::vector<std::vector<MatchingType>> all_matchings;
1634 std::vector<int> sizes;
1635 Timer const time_preprocess_bary;
1636 std::vector<BidderDiagram> diagrams_c_min;
1641 sizes.resize(diagrams_c_min.size());
1642 for(
size_t i = 0; i < diagrams_c_min.size(); i++) {
1643 sizes[i] = diagrams_c_min[i].size();
1648 std::vector<GoodDiagram> barycenter_goods(
clustering_[c].size());
1649 for(
size_t i_diagram = 0; i_diagram <
clustering_[c].size();
1651 barycenter_goods[i_diagram]
1655 all_matchings.resize(diagrams_c_min.size());
1663 diagrams_c_min.resize(
1665 all_matchings.resize(
1670 bool use_kdt =
false;
1677 &total_cost,
epsilon_[0], sizes, *pair.first, pair.second,
1678 &(min_diag_price->at(0)), &(min_price->at(0)), &(all_matchings),
1679 use_kdt, only_matchings);
1680 for(
size_t ii = 0; ii < all_matchings.size(); ii++) {
1681 all_matchings_per_type_and_cluster[c][0][ii].resize(
1682 all_matchings[ii].size());
1683 all_matchings_per_type_and_cluster[c][0][ii] = all_matchings[ii];
1686 all_matchings_per_type_and_cluster[c][0][ii].resize(0);
1692 Timer const time_update;
1693 if(!only_matchings) {
1698 if(max_shift_c_min > max_shift_vector[0]) {
1699 max_shift_vector[0] = max_shift_c_min;
1705 centroids_with_price_min
1725 std::vector<std::vector<MatchingType>> all_matchings;
1727 std::vector<int> sizes;
1729 std::vector<BidderDiagram> diagrams_c_min;
1734 sizes.resize(diagrams_c_min.size());
1735 for(
size_t i = 0; i < diagrams_c_min.size(); i++) {
1736 sizes[i] = diagrams_c_min[i].size();
1740 std::vector<GoodDiagram> barycenter_goods(
clustering_[c].size());
1741 for(
size_t i_diagram = 0; i_diagram <
clustering_[c].size();
1743 barycenter_goods[i_diagram]
1747 all_matchings.resize(diagrams_c_min.size());
1755 all_matchings.resize(
1757 diagrams_c_min.resize(
1762 bool use_kdt =
false;
1769 &total_cost,
epsilon_[1], sizes, *pair.first, pair.second,
1770 &(min_diag_price->at(1)), &(min_price->at(1)), &(all_matchings),
1771 use_kdt, only_matchings);
1772 for(
size_t ii = 0; ii < all_matchings.size(); ii++) {
1773 all_matchings_per_type_and_cluster[c][1][ii].resize(
1774 all_matchings[ii].size());
1775 all_matchings_per_type_and_cluster[c][1][ii] = all_matchings[ii];
1778 all_matchings_per_type_and_cluster[c][1][ii].resize(0);
1783 if(!only_matchings) {
1790 if(max_shift_c_sad > max_shift_vector[1]) {
1791 max_shift_vector[1] = max_shift_c_sad;
1797 centroids_with_price_sad
1814 std::vector<std::vector<MatchingType>> all_matchings;
1815 Timer const time_preprocess_bary;
1817 std::vector<int> sizes;
1818 std::vector<BidderDiagram> diagrams_c_min;
1823 sizes.resize(diagrams_c_min.size());
1824 for(
size_t i = 0; i < diagrams_c_min.size(); i++) {
1825 sizes[i] = diagrams_c_min[i].size();
1829 std::vector<GoodDiagram> barycenter_goods(
clustering_[c].size());
1830 for(
size_t i_diagram = 0; i_diagram <
clustering_[c].size();
1832 barycenter_goods[i_diagram]
1836 all_matchings.resize(diagrams_c_min.size());
1845 diagrams_c_min.resize(
1847 all_matchings.resize(
1852 bool use_kdt =
false;
1859 &total_cost,
epsilon_[2], sizes, *pair.first, pair.second,
1860 &(min_diag_price->at(2)), &(min_price->at(2)), &(all_matchings),
1861 use_kdt, only_matchings);
1862 for(
size_t ii = 0; ii < all_matchings.size(); ii++) {
1863 all_matchings_per_type_and_cluster[c][2][ii].resize(
1864 all_matchings[ii].size());
1865 all_matchings_per_type_and_cluster[c][2][ii] = all_matchings[ii];
1868 all_matchings_per_type_and_cluster[c][2][ii].resize(0);
1874 Timer const time_update;
1875 if(!only_matchings) {
1879 if(max_shift_c_max > max_shift_vector[2]) {
1880 max_shift_vector[2] = max_shift_c_max;
1886 centroids_with_price_max
1904 if(wasserstein_shift > max_wasserstein_shift) {
1905 max_wasserstein_shift = wasserstein_shift;
1940 return max_shift_vector;
2010 std::vector<double> &previous_min_persistence,
2011 std::vector<double> &min_persistence,
2012 std::vector<std::vector<double>> &initial_diagonal_prices,
2013 std::vector<std::vector<double>> &initial_off_diagonal_prices,
2014 std::vector<int> &min_points_to_add,
2015 bool add_points_to_barycenter,
2016 bool first_enrichment) {
2018 std::vector<double> new_min_persistence = min_persistence;
2021 new_min_persistence[0] = previous_min_persistence[0];
2024 new_min_persistence[1] = previous_min_persistence[1];
2027 new_min_persistence[2] = previous_min_persistence[2];
2032 size_t max_diagram_size_min{};
2033 size_t max_diagram_size_sad{};
2034 size_t max_diagram_size_max{};
2056 int const max_points_to_add_min
2057 = std::max(min_points_to_add[0],
2058 min_points_to_add[0] + (
int)(max_diagram_size_min / 10));
2059 int const max_points_to_add_sad
2060 = std::max(min_points_to_add[1],
2061 min_points_to_add[1] + (
int)(max_diagram_size_sad / 10));
2062 int const max_points_to_add_max
2063 = std::max(min_points_to_add[2],
2064 min_points_to_add[2] + (
int)(max_diagram_size_max / 10));
2067 std::vector<std::vector<int>> candidates_to_be_added_min(
numberOfInputs_);
2068 std::vector<std::vector<int>> candidates_to_be_added_sad(
numberOfInputs_);
2069 std::vector<std::vector<int>> candidates_to_be_added_max(
numberOfInputs_);
2076 std::vector<double> persistences;
2080 if(persistence >= min_persistence[0]
2081 && persistence <= previous_min_persistence[0]) {
2082 candidates_to_be_added_min[i].emplace_back(j);
2083 idx_min[i].emplace_back(idx_min[i].size());
2084 persistences.emplace_back(persistence);
2088 idx_min[i].
begin(), idx_min[i].
end(), [&persistences](
int &a,
int &b) {
2089 return ((persistences[a] > persistences[b])
2090 || ((persistences[a] == persistences[b]) && (a > b)));
2092 int const size = candidates_to_be_added_min[i].size();
2093 if(size >= max_points_to_add_min) {
2094 double const last_persistence_added_min
2095 = persistences[idx_min[i][max_points_to_add_min - 1]];
2096 if(first_enrichment) {
2099 new_min_persistence[0] = last_persistence_added_min;
2101 if(last_persistence_added_min < new_min_persistence[0])
2102 new_min_persistence[0] = last_persistence_added_min;
2105 if(last_persistence_added_min > new_min_persistence[0]) {
2106 new_min_persistence[0] = last_persistence_added_min;
2115 std::vector<double> persistences;
2119 if(persistence >= min_persistence[1]
2120 && persistence <= previous_min_persistence[1]) {
2121 candidates_to_be_added_sad[i].emplace_back(j);
2122 idx_sad[i].emplace_back(idx_sad[i].size());
2123 persistences.emplace_back(persistence);
2127 idx_sad[i].
begin(), idx_sad[i].
end(), [&persistences](
int &a,
int &b) {
2128 return ((persistences[a] > persistences[b])
2129 || ((persistences[a] == persistences[b]) && (a > b)));
2131 int const size = candidates_to_be_added_sad[i].size();
2132 if(size >= max_points_to_add_sad) {
2133 double const last_persistence_added_sad
2134 = persistences[idx_sad[i][max_points_to_add_sad - 1]];
2135 if(first_enrichment) {
2138 new_min_persistence[1] = last_persistence_added_sad;
2140 if(last_persistence_added_sad < new_min_persistence[1])
2141 new_min_persistence[1] = last_persistence_added_sad;
2144 if(last_persistence_added_sad > new_min_persistence[1]) {
2145 new_min_persistence[1] = last_persistence_added_sad;
2153 std::vector<double> persistences;
2157 if(persistence >= min_persistence[2]
2158 && persistence <= previous_min_persistence[2]) {
2159 candidates_to_be_added_max[i].emplace_back(j);
2160 idx_max[i].emplace_back(idx_max[i].size());
2161 persistences.emplace_back(persistence);
2165 idx_max[i].
begin(), idx_max[i].
end(), [&persistences](
int &a,
int &b) {
2166 return ((persistences[a] > persistences[b])
2167 || ((persistences[a] == persistences[b]) && (a > b)));
2169 int const size = candidates_to_be_added_max[i].size();
2170 if(size >= max_points_to_add_max) {
2171 double const last_persistence_added_max
2172 = persistences[idx_max[i][max_points_to_add_max - 1]];
2173 if(first_enrichment) {
2176 new_min_persistence[2] = last_persistence_added_max;
2178 if(last_persistence_added_max < new_min_persistence[2])
2179 new_min_persistence[2] = last_persistence_added_max;
2182 if(last_persistence_added_max > new_min_persistence[2]) {
2183 new_min_persistence[2] = last_persistence_added_max;
2192 int counter_for_adding_points = 0;
2194 int const size = candidates_to_be_added_min[i].size();
2195 for(
int j = 0; j < std::min(max_points_to_add_min, size); j++) {
2197 candidates_to_be_added_min[i][idx_min[i][j]]);
2199 if(persistence >= new_min_persistence[0]) {
2205 [candidates_to_be_added_min[i][idx_min[i][j]]]
2209 for(
int c = 0; c <
k_; ++c) {
2214 - persistence / sqrt(2),
2227 int const to_be_added_to_barycenter
2230 if(to_be_added_to_barycenter == 0 && add_points_to_barycenter) {
2235 g.
setPrice(initial_off_diagonal_prices[0][k]);
2247 counter_for_adding_points++;
2252 int counter_for_adding_points = 0;
2254 int const size = candidates_to_be_added_sad[i].size();
2255 for(
int j = 0; j < std::min(max_points_to_add_sad, size); j++) {
2257 candidates_to_be_added_sad[i][idx_sad[i][j]]);
2259 if(persistence >= new_min_persistence[1]) {
2265 [candidates_to_be_added_sad[i][idx_sad[i][j]]]
2269 for(
int c = 0; c <
k_; ++c) {
2274 - persistence / sqrt(2),
2287 int const to_be_added_to_barycenter
2290 if(to_be_added_to_barycenter == 0 && add_points_to_barycenter) {
2295 g.
setPrice(initial_off_diagonal_prices[1][k]);
2303 counter_for_adding_points++;
2308 int counter_for_adding_points = 0;
2310 int const size = candidates_to_be_added_max[i].size();
2311 for(
int j = 0; j < std::min(max_points_to_add_max, size); j++) {
2313 candidates_to_be_added_max[i][idx_max[i][j]]);
2315 if(persistence >= new_min_persistence[2]) {
2321 [candidates_to_be_added_max[i][idx_max[i][j]]]
2325 for(
int c = 0; c <
k_; ++c) {
2330 - persistence / sqrt(2),
2343 int const to_be_added_to_barycenter
2346 if(to_be_added_to_barycenter == 0 && add_points_to_barycenter) {
2351 g.
setPrice(initial_off_diagonal_prices[2][k]);
2363 counter_for_adding_points++;
2368 return new_min_persistence;
2581 std::vector<std::vector<MatchingType>> &matchings,
2582 std::vector<std::vector<int>> &bidders_ids,
2583 std::vector<BidderDiagram> ¤t_bidder_diagrams,
2584 std::vector<BidderDiagram> &bidder_diagrams,
2587 auto &matchings0 = matchings[0];
2588 auto &diagram0 = bidder_diagrams[0];
2589 auto ¤t_diagram0 = current_bidder_diagrams[0];
2590 auto &ids0 = bidders_ids[0];
2592 auto &matchings1 = matchings[1];
2593 auto &diagram1 = bidder_diagrams[1];
2594 auto ¤t_diagram1 = current_bidder_diagrams[1];
2595 auto &ids1 = bidders_ids[1];
2597 std::vector<int> new_to_old_id(current_diagram1.size());
2599 for(
size_t j = 0; j < ids1.size(); j++) {
2600 int const new_id = ids1[j];
2602 new_to_old_id[new_id] = j;
2606 std::vector<MatchingType> matching_to_add(0);
2607 std::vector<MatchingType> matching_to_add2(0);
2609 for(
size_t i = 0; i < matchings1.size(); i++) {
2611 int const bidderId = std::get<0>(t);
2612 int const goodId = std::get<1>(t);
2615 Bidder const b = diagram1.at(new_to_old_id[bidderId]);
2616 double const bx = b.
x_;
2617 double const by = b.
y_;
2619 Good const g = barycenter.at(goodId);
2620 double const gx = g.
x_;
2621 double const gy = g.
y_;
2622 barycenter.at(goodId).x_ = (bx + gx) / 2;
2623 barycenter.at(goodId).y_ = (by + gy) / 2;
2626 std::get<2>(t) /= 4;
2629 double gx = (bx + by) / 2;
2630 double gy = (bx + by) / 2;
2637 = std::make_tuple(bidderId, barycenter.size(), cost);
2638 MatchingType const t3 = std::make_tuple(-1, barycenter.size(), cost);
2639 Good const g =
Good(gx, gy,
false, barycenter.size());
2641 barycenter.emplace_back(g);
2642 matching_to_add.emplace_back(t2);
2643 matching_to_add2.emplace_back(t3);
2647 Good const g = barycenter.at(goodId);
2648 double const gx = (g.
x_ + g.
y_) / 2;
2649 double const gy = (g.
x_ + g.
y_) / 2;
2650 barycenter.at(goodId).
x_ = (gx + g.
x_) / 2;
2651 barycenter.at(goodId).y_ = (gy + g.
y_) / 2;
2652 std::get<2>(t) /= 4;
2656 for(
size_t j = 0; j < matching_to_add.size(); j++) {
2657 matchings1.emplace_back(matching_to_add[j]);
2659 for(
size_t j = 0; j < matching_to_add2.size(); j++) {
2660 matchings0.emplace_back(matching_to_add2[j]);
2666 std::vector<int> new_to_old_id2(current_diagram0.size());
2668 for(
size_t j = 0; j < ids0.size(); j++) {
2669 int const new_id = ids0[j];
2671 new_to_old_id2[new_id] = j;
2675 for(
size_t i = 0; i < matchings0.size(); i++) {
2677 int const bidderId = std::get<0>(t);
2678 int const goodId = std::get<1>(t);
2680 if(bidderId >= 0 and goodId >= 0) {
2681 Bidder const b = diagram0.at(new_to_old_id2[bidderId]);
2682 double const bx = b.
x_;
2683 double const by = b.
y_;
2684 Good const g = barycenter.at(goodId);
2685 double const gx = g.
x_;
2686 double const gy = g.
y_;
2689 std::get<2>(t) = cost;