TTK
Loading...
Searching...
No Matches
PersistenceDiagramAuction.h
Go to the documentation of this file.
1#pragma once
2
4
5#include <limits>
6
7namespace ttk {
9
10 public:
12 return bidders_.size();
13 }
14
16
19 std::vector<KDT *> default_correspondence_kdt_map_{};
22
23 inline void initLowerBoundCostWeight(double delta_lim) {
24 lowerBoundCostWeight_ = 1 + delta_lim;
25 }
26
27 double initLowerBoundCost(const int kdt_index = 0);
28
30 double geometricalFactor,
31 double lambda,
32 double delta_lim,
33 bool use_kdTree,
34 double nonMatchingWeight = 1.0)
35 : wasserstein_{wasserstein}, geometricalFactor_{geometricalFactor},
36 lambda_{lambda}, delta_lim_{delta_lim}, use_kdt_{use_kdTree},
37 nonMatchingWeight_{nonMatchingWeight} {
38 }
39
41 GoodDiagram &goods,
42 int wasserstein,
43 double geometricalFactor,
44 double lambda,
45 double delta_lim,
46 KDT &kdt,
47 std::vector<KDT *> &correspondence_kdt_map,
48 double epsilon = {},
49 double initial_diag_price = {},
50 bool use_kdTree = true,
51 double nonMatchingWeight = 1.0)
52 : kdt_{kdt}, correspondence_kdt_map_{correspondence_kdt_map},
53 bidders_{bidders}, goods_{goods} {
54
55 n_bidders_ = bidders.size();
56 n_goods_ = goods.size();
57
58 for(int i = 0; i < n_bidders_; i++) {
59 // Add diagonal goods
60 Bidder const &b = bidders_[i];
61 Good g{b.x_, b.y_, true, -b.id_ - 1};
62 g.projectOnDiagonal();
63 if(b.diagonal_price_ > 0) {
64 g.setPrice(b.diagonal_price_);
65 } else {
66 g.setPrice(initial_diag_price);
67 }
68 diagonal_goods_.emplace_back(g);
69 std::pair<int, double> const pair = std::make_pair(i, g.getPrice());
70 diagonal_queue_.push(pair);
71 }
72 for(int i = 0; i < n_goods_; i++) {
73 // Add diagonal bidders
74 Good const &g = goods_[i];
75 Bidder b{g.x_, g.y_, true, -g.id_ - 1};
76 b.projectOnDiagonal();
77 b.setPositionInAuction(bidders_.size());
78 bidders_.emplace_back(b);
79 }
80
81 epsilon_ = epsilon;
82 wasserstein_ = wasserstein;
83 delta_lim_ = delta_lim;
84 geometricalFactor_ = geometricalFactor;
85 lambda_ = lambda;
86 nonMatchingWeight_ = nonMatchingWeight;
87
88 use_kdt_ = (use_kdTree && !goods_.empty());
89 }
90
91 void runAuctionRound(int &n_biddings, const int kdt_index = 0);
92 double getMatchingsAndDistance(std::vector<MatchingType> &matchings,
93 bool get_diagonal_matches = false);
94 double run(std::vector<MatchingType> &matchings, const int kdt_index = 0);
95 double run() {
96 std::vector<MatchingType> matchings{};
97 return this->run(matchings);
98 }
99 double getMaximalPrice();
100
101 void BuildAuctionDiagrams(const BidderDiagram &BD, const GoodDiagram &GD) {
102 this->n_bidders_ = BD.size();
103 this->n_goods_ = GD.size();
104 // delete_kdTree_ = false;
105 this->bidders_ = BD;
106 this->goods_ = GD;
107
108 for(int i = 0; i < n_bidders_; i++) {
109 // Add diagonal goods
110 Bidder const &b = bidders_[i];
111 Good g{b.x_, b.y_, true, -b.id_ - 1};
112 g.projectOnDiagonal();
113 diagonal_goods_.emplace_back(g);
114 std::pair<int, double> const pair = std::make_pair(i, g.getPrice());
115 diagonal_queue_.push(pair);
116 }
117 for(int i = 0; i < n_goods_; i++) {
118 // Add diagonal bidders
119 Good const &g = goods_[i];
120 Bidder b{g.x_, g.y_, true, -g.id_ - 1};
121 b.projectOnDiagonal();
122 b.setPositionInAuction(bidders_.size());
123 bidders_.emplace_back(b);
124 }
125 if(!goods_.empty()) {
126 // use_kdt_ = use_kdt_;
127 this->buildKDTree();
128 } else {
129 use_kdt_ = false;
130 }
131 }
132
133 void BuildAuctionDiagrams(const DiagramType &diagram1,
134 const DiagramType &diagram2) {
135 n_bidders_ = diagram1.size();
136 n_goods_ = diagram2.size();
137 this->setBidders(diagram1);
138 this->setGoods(diagram2);
139 for(int i = 0; i < n_bidders_; i++) {
140 // Add diagonal goods
141 Bidder const &b = bidders_[i];
142 Good g{b.x_, b.y_, true, -b.id_ - 1};
143 g.projectOnDiagonal();
144 diagonal_goods_.emplace_back(g);
145 std::pair<int, double> const pair = std::make_pair(i, g.getPrice());
146 diagonal_queue_.push(pair);
147 }
148 for(int i = 0; i < n_goods_; i++) {
149 // Add diagonal bidders
150 Good const &g = goods_[i];
151 Bidder b{g.x_, g.y_, true, -g.id_ - 1};
152 b.projectOnDiagonal();
153 b.setPositionInAuction(bidders_.size());
154 bidders_.emplace_back(b);
155 }
156 if(!bidders_.empty()) {
157 use_kdt_ = true;
158 this->buildKDTree();
159 } else {
160 use_kdt_ = false;
161 }
162 }
163
164 void setBidders(const DiagramType &diagram1) {
165 for(size_t i = 0; i < diagram1.size(); i++) {
166 // Add bidder to bidders
167 Bidder b{diagram1[i], static_cast<int>(i), lambda_};
169 bidders_.emplace_back(b);
170 }
171 n_bidders_ = bidders_.size();
172 }
173
174 void setGoods(const DiagramType &diagram2) {
175 for(size_t i = 0; i < diagram2.size(); i++) {
176 // Add bidder to bidders
177 Good const g{diagram2[i], static_cast<int>(i), lambda_};
178 goods_.emplace_back(g);
179 }
180 n_goods_ = goods_.size();
181 }
182
183 void buildKDTree() {
184 Timer const t;
186 const int dimension
187 = geometricalFactor_ >= 1 ? (geometricalFactor_ <= 0 ? 3 : 2) : 5;
188 std::vector<double> coordinates;
189 for(size_t i = 0; i < goods_.size(); i++) {
190 Good &g = goods_[i];
191 if(geometricalFactor_ > 0) {
192 coordinates.push_back(geometricalFactor_ * g.x_);
193 coordinates.push_back(geometricalFactor_ * g.y_);
194 }
195 if(geometricalFactor_ < 1) {
196 coordinates.push_back((1 - geometricalFactor_) * g.coords_[0]);
197 coordinates.push_back((1 - geometricalFactor_) * g.coords_[1]);
198 coordinates.push_back((1 - geometricalFactor_) * g.coords_[2]);
199 }
200 }
202 = kdt_.build(coordinates.data(), goods_.size(), dimension);
203 }
204
205 void setEpsilon(const double epsilon) {
206 epsilon_ = epsilon;
207 }
208
210 double max_persistence = 0;
211 for(const auto &b : this->bidders_) {
212 double const persistence = b.getPersistence();
213 if(persistence > max_persistence) {
214 max_persistence = persistence;
215 }
216 }
217 for(const auto &g : this->goods_) {
218 double const persistence = g.getPersistence();
219 if(persistence > max_persistence) {
220 max_persistence = persistence;
221 }
222 }
223 this->epsilon_ = 5.0 / 4 * Geometry::pow(max_persistence, wasserstein_);
224 }
225
227 for(size_t i = 0; i < bidders_.size(); i++) {
228 Bidder &b = bidders_[i];
229 b.resetProperty();
230 unassignedBidders_.push(i);
231 }
232 }
233
235 for(auto &g : this->goods_) {
236 g.setOwner(-1);
237 }
238 for(auto &g : this->diagonal_goods_) {
239 g.setOwner(-1);
240 }
241 }
242
244 double d = 0;
245 for(size_t i = 0; i < bidders_.size(); i++) {
246 Bidder const &b = bidders_[i];
249 }
250 return d;
251 }
252
254 double const d = this->getMatchingDistance();
255 if(d < 1e-6 or d <= (lowerBoundCost_ * lowerBoundCostWeight_)) {
256 return 0;
257 }
258 double const denominator = d - bidders_.size() * epsilon_;
259 if(denominator <= 0) {
260 return std::numeric_limits<double>::max();
261 } else {
262 return Geometry::pow(d / denominator, 1 / ((float)wasserstein_)) - 1;
263 }
264 }
265
267 for(size_t i = 0; i < diagonal_goods_.size(); i++) {
268 Bidder &b = bidders_[i];
269 b.setDiagonalPrice(diagonal_goods_[i].getPrice());
270 }
271 }
272
274 if(diagonal_goods_.empty()) {
275 return 0;
276 }
277 double min_price = std::numeric_limits<double>::max();
278 for(size_t i = 0; i < diagonal_goods_.size(); i++) {
279 double const price = diagonal_goods_[i].getPrice();
280 if(price < min_price) {
281 min_price = price;
282 }
283 }
284 return min_price;
285 }
286
287 protected:
288 int wasserstein_{2}; // Power in Wassertsein distance (by default set to 2)
294 std::priority_queue<std::pair<int, double>,
295 std::vector<std::pair<int, double>>,
296 Compare>
298 std::queue<int> unassignedBidders_{};
299
301 int n_goods_{0};
302
303 double epsilon_{1};
305 double lambda_{};
306 // lambda : 0<=lambda<=1
307 // parametrizes the point used for the physical (critical) coordinates of
308 // the persistence paired lambda = 1 : extremum (min if pair min-sad, max if
309 // pair sad-max) lambda = 0 : saddle (bad stability) lambda = 1/2 : middle
310 // of the 2 critical points of the pair
311 double delta_lim_{};
313 bool use_kdt_{true};
314 double nonMatchingWeight_ = 1.0;
315
316 }; // namespace ttk
317} // namespace ttk
void setDiagonalPrice(const double price)
void setPositionInAuction(const int pos)
KDTree< double, std::array< double, 5 > > KDT
const Good & getProperty() const
Minimalist debugging class.
Definition Debug.h:88
TTK KD-Tree.
Definition KDTree.h:21
KDTreeMap build(dataType *data, const int &ptNumber, const int &dimension, const std::vector< std::vector< dataType > > &weights={}, const int &weightNumber=1, const int &nodeNumber=-1, const bool &preciseBoundingBox=false)
Definition KDTree.h:154
int id_
Definition KDTree.h:44
double cost(const PersistenceDiagramAuctionActor &g, const int wasserstein, const double geometricalFactor, const double nonMatchingWeight) const
void runAuctionRound(int &n_biddings, const int kdt_index=0)
std::vector< KDT * > & correspondence_kdt_map_
PersistenceDiagramAuction(int wasserstein, double geometricalFactor, double lambda, double delta_lim, bool use_kdTree, double nonMatchingWeight=1.0)
PersistenceDiagramAuction(BidderDiagram &bidders, GoodDiagram &goods, int wasserstein, double geometricalFactor, double lambda, double delta_lim, KDT &kdt, std::vector< KDT * > &correspondence_kdt_map, double epsilon={}, double initial_diag_price={}, bool use_kdTree=true, double nonMatchingWeight=1.0)
std::priority_queue< std::pair< int, double >, std::vector< std::pair< int, double > >, Compare > diagonal_queue_
void BuildAuctionDiagrams(const DiagramType &diagram1, const DiagramType &diagram2)
double initLowerBoundCost(const int kdt_index=0)
double getMatchingsAndDistance(std::vector< MatchingType > &matchings, bool get_diagonal_matches=false)
std::vector< KDT * > default_correspondence_kdt_map_
void BuildAuctionDiagrams(const BidderDiagram &BD, const GoodDiagram &GD)
void initLowerBoundCostWeight(double delta_lim)
void setGoods(const DiagramType &diagram2)
void setBidders(const DiagramType &diagram1)
T1 pow(const T1 val, const T2 n)
Definition Geometry.h:454
The Topology ToolKit.
std::vector< Bidder > BidderDiagram
std::vector< PersistencePair > DiagramType
Persistence Diagram type as a vector of Persistence pairs.
std::vector< Good > GoodDiagram