Loading...
Searching...
No Matches
base_pairing.h
Go to the documentation of this file.
1/* This file is part of the Gudhi Library - https://gudhi.inria.fr/ - which is released under MIT.
2 * See file LICENSE or go to https://gudhi.inria.fr/licensing/ for full license details.
3 * Author(s): Hannah Schreiber
4 *
5 * Copyright (C) 2022-24 Inria
6 *
7 * Modification(s):
8 * - YYYY/MM Author: Description of the modification
9 */
10
17#ifndef PM_BASE_PAIRING_H
18#define PM_BASE_PAIRING_H
19
20#include <utility> //std::swap & std::move
21#include <unordered_map>
22#include <algorithm>
23#include <vector>
24
25namespace Gudhi {
26namespace persistence_matrix {
27
36 friend void swap([[maybe_unused]] Dummy_base_pairing& d1, [[maybe_unused]] Dummy_base_pairing& d2) {}
37};
38
47template <class Master_matrix>
49{
50 public:
51 using Bar = typename Master_matrix::Bar;
52 using barcode_type = typename Master_matrix::barcode_type;
53 using matrix_type = typename Master_matrix::column_container_type;
54 using index = typename Master_matrix::index;
55 using dimension_type = typename Master_matrix::dimension_type;
66 Base_pairing(const Base_pairing& matrixToCopy);
72 Base_pairing(Base_pairing&& other) noexcept;
73
84
92 friend void swap(Base_pairing& pairing1, Base_pairing& pairing2) {
93 pairing1.barcode_.swap(pairing2.barcode_);
94 pairing1.deathToBar_.swap(pairing2.deathToBar_);
95 std::swap(pairing1.isReduced_, pairing2.isReduced_);
96 }
97
98 protected:
99 using pos_index = typename Master_matrix::pos_index;
100 using dictionnary_type = typename Master_matrix::bar_dictionnary_type;
101 using base_matrix = typename Master_matrix::Boundary_matrix_type;
102
103 barcode_type barcode_;
104 dictionnary_type deathToBar_;
105 bool isReduced_;
107 void _reduce();
108 void _remove_last(pos_index columnIndex);
109
110 //access to inheritating Boundary_matrix class
111 constexpr base_matrix* _matrix() { return static_cast<base_matrix*>(this); }
112 constexpr const base_matrix* _matrix() const { return static_cast<const base_matrix*>(this); }
113};
114
115template <class Master_matrix>
116inline Base_pairing<Master_matrix>::Base_pairing() : isReduced_(false)
117{}
118
119template <class Master_matrix>
121 : barcode_(matrixToCopy.barcode_), deathToBar_(matrixToCopy.deathToBar_), isReduced_(matrixToCopy.isReduced_)
122{}
123
124template <class Master_matrix>
126 : barcode_(std::move(other.barcode_)),
127 deathToBar_(std::move(other.deathToBar_)),
128 isReduced_(std::move(other.isReduced_))
129{}
130
131template <class Master_matrix>
133{
134 if (!isReduced_) _reduce();
135 return barcode_;
136}
137
138template <class Master_matrix>
140{
141 using id_index = typename Master_matrix::index;
142 std::unordered_map<id_index, index> pivotsToColumn(_matrix()->get_number_of_columns());
143
144 auto dim = _matrix()->get_max_dimension();
145 std::vector<std::vector<index> > columnsByDim(dim + 1);
146 for (unsigned int i = 0; i < _matrix()->get_number_of_columns(); i++) {
147 columnsByDim[dim - _matrix()->get_column_dimension(i)].push_back(i);
148 }
149
150 for (const auto& cols : columnsByDim) {
151 for (index i : cols) {
152 auto& curr = _matrix()->get_column(i);
153 if (curr.is_empty()) {
154 if (pivotsToColumn.find(i) == pivotsToColumn.end()) {
155 barcode_.emplace_back(dim, i, -1);
156 }
157 } else {
158 id_index pivot = curr.get_pivot();
159
160 while (pivot != static_cast<id_index>(-1) && pivotsToColumn.find(pivot) != pivotsToColumn.end()) {
161 if constexpr (Master_matrix::Option_list::is_z2) {
162 curr += _matrix()->get_column(pivotsToColumn.at(pivot));
163 } else {
164 auto& toadd = _matrix()->get_column(pivotsToColumn.at(pivot));
165 typename Master_matrix::element_type coef = toadd.get_pivot_value();
166 auto& operators = _matrix()->colSettings_->operators;
167 coef = operators.get_inverse(coef);
168 operators.multiply_inplace(coef, operators.get_characteristic() - curr.get_pivot_value());
169 curr.multiply_source_and_add(toadd, coef);
170 }
171
172 pivot = curr.get_pivot();
173 }
174
175 if (pivot != static_cast<id_index>(-1)) {
176 pivotsToColumn.emplace(pivot, i);
177 _matrix()->get_column(pivot).clear();
178 barcode_.emplace_back(dim - 1, pivot, i);
179 } else {
180 curr.clear();
181 barcode_.emplace_back(dim, i, -1);
182 }
183 }
184 }
185 --dim;
186 }
187
188 if constexpr (Master_matrix::Option_list::has_removable_columns) {
189 // sort barcode by birth such that a removal is trivial
190 std::sort(barcode_.begin(), barcode_.end(), [](const Bar& b1, const Bar& b2) { return b1.birth < b2.birth; });
191 // map can only be constructed once barcode is sorted
192 for (index i = 0; i < barcode_.size(); ++i) {
193 auto d = barcode_[i].death;
194 if (d != static_cast<pos_index>(-1)) {
195 deathToBar_.emplace(d, i);
196 }
197 }
198 }
199
200 isReduced_ = true;
201}
202
203template <class Master_matrix>
204inline void Base_pairing<Master_matrix>::_remove_last(pos_index columnIndex)
205{
206 static_assert(Master_matrix::Option_list::has_removable_columns, "remove_last not available.");
207
208 if (isReduced_) {
209 auto it = deathToBar_.find(columnIndex);
210
211 if (it == deathToBar_.end()) { // birth
212 barcode_.pop_back(); // sorted by birth and columnIndex has to be the heighest one
213 } else { // death
214 barcode_[it->second].death = -1;
215 deathToBar_.erase(it);
216 };
217 }
218}
219
220template <class Master_matrix>
222{
223 barcode_.swap(other.barcode_);
224 deathToBar_.swap(other.deathToBar_);
225 std::swap(isReduced_, other.isReduced_);
226 return *this;
227}
228
229} // namespace persistence_matrix
230} // namespace Gudhi
231
232#endif // PM_BASE_PAIRING_H
Class managing the barcode for Boundary_matrix if the option was enabled.
Definition base_pairing.h:49
typename Master_matrix::barcode_type barcode_type
Definition base_pairing.h:52
typename Master_matrix::Bar Bar
Definition base_pairing.h:51
typename Master_matrix::index index
Definition base_pairing.h:54
friend void swap(Base_pairing &pairing1, Base_pairing &pairing2)
Swap operator.
Definition base_pairing.h:92
Base_pairing & operator=(Base_pairing other)
Assign operator.
Definition base_pairing.h:221
typename Master_matrix::column_container_type matrix_type
Definition base_pairing.h:53
typename Master_matrix::dimension_type dimension_type
Definition base_pairing.h:55
const barcode_type & get_current_barcode()
Reduces the matrix stored in Boundary_matrix and computes the corresponding barcode.
Definition base_pairing.h:132
Base_pairing()
Default constructor.
Definition base_pairing.h:116
Gudhi namespace.
Definition SimplicialComplexForAlpha.h:14
Empty structure. Inheritated instead of Base_pairing, when the computation of the barcode was not ena...
Definition base_pairing.h:35