All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Modules Pages
Position_to_index_overlay.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_POS_TO_ID_TRANSLATION_H
18#define PM_POS_TO_ID_TRANSLATION_H
19
20#include <vector>
21#include <utility> //std::swap, std::move & std::exchange
22#include <algorithm> //std::transform
23
24namespace Gudhi {
25namespace persistence_matrix {
26
38template <class Underlying_matrix, class Master_matrix>
40{
41 public:
42 using Index = typename Master_matrix::Index;
43 using ID_index = typename Master_matrix::ID_index;
44 using Pos_index = typename Master_matrix::Pos_index;
45 using Dimension = typename Master_matrix::Dimension;
49 using Field_operators = typename Master_matrix::Field_operators;
50 using Field_element = typename Master_matrix::Element;
51 using Boundary = typename Master_matrix::Boundary;
52 using Column = typename Master_matrix::Column;
53 using Row = typename Master_matrix::Row;
55 using Bar = typename Master_matrix::Bar;
56 using Barcode = typename Master_matrix::Barcode;
57 using Cycle = typename Master_matrix::Cycle;
58 using Entry_representative = typename Master_matrix::Entry_representative;
59 using Entry_constructor = typename Master_matrix::Entry_constructor;
60 using Column_settings = typename Master_matrix::Column_settings;
91 template <class Boundary_range = Boundary>
92 Position_to_index_overlay(const std::vector<Boundary_range>& orderedBoundaries,
93 Column_settings* colSettings);
101 Position_to_index_overlay(unsigned int numberOfColumns,
102 Column_settings* colSettings);
125 template <typename BirthComparatorFunction, typename DeathComparatorFunction>
127 const BirthComparatorFunction& birthComparator,
128 const DeathComparatorFunction& deathComparator);
165 template <typename BirthComparatorFunction, typename DeathComparatorFunction, class Boundary_range>
166 Position_to_index_overlay(const std::vector<Boundary_range>& orderedBoundaries,
167 Column_settings* colSettings,
168 const BirthComparatorFunction& birthComparator,
169 const DeathComparatorFunction& deathComparator);
193 template <typename BirthComparatorFunction, typename DeathComparatorFunction>
194 Position_to_index_overlay(unsigned int numberOfColumns,
195 Column_settings* colSettings,
196 const BirthComparatorFunction& birthComparator,
197 const DeathComparatorFunction& deathComparator);
208 Column_settings* colSettings = nullptr);
215
236 template <class Boundary_range = Boundary>
237 void insert_boundary(const Boundary_range& boundary,
238 Dimension dim = Master_matrix::template get_null_value<Dimension>());
256 template <class Boundary_range = Boundary>
257 void insert_boundary(ID_index cellIndex, const Boundary_range& boundary,
258 Dimension dim = Master_matrix::template get_null_value<Dimension>());
266 Column& get_column(Pos_index position);
274 const Column& get_column(Pos_index position) const;
283 Row& get_row(ID_index rowIndex);
292 const Row& get_row(ID_index rowIndex) const;
307 void erase_empty_row(ID_index rowIndex);
321 void remove_maximal_cell(Pos_index position);
330 void remove_last();
331
352
363 void add_to(Pos_index sourcePosition, Pos_index targetPosition);
376 void multiply_target_and_add_to(Pos_index sourcePosition,
377 const Field_element& coefficient,
378 Pos_index targetPosition);
391 void multiply_source_and_add_to(const Field_element& coefficient,
392 Pos_index sourcePosition,
393 Pos_index targetPosition);
394
403 bool is_zero_entry(Pos_index position, ID_index rowIndex) const;
414 bool is_zero_column(Pos_index position);
415
423 Pos_index get_column_with_pivot(ID_index cellIndex) const; // assumes that pivot exists
430 ID_index get_pivot(Pos_index position);
431
438 void reset(Column_settings* colSettings) {
439 matrix_.reset(colSettings);
440 positionToIndex_.clear();
441 nextPosition_ = 0;
442 nextIndex_ = 0;
443 }
444
445 // void set_operators(Field_operators* operators) { matrix_.set_operators(operators); }
446
455 swap(matrix1.matrix_, matrix2.matrix_);
456 matrix1.positionToIndex_.swap(matrix2.positionToIndex_);
457 std::swap(matrix1.nextPosition_, matrix2.nextPosition_);
458 std::swap(matrix1.nextIndex_, matrix2.nextIndex_);
459 }
460
461 void print(); // for debug
462
463 // access to optional methods
464
474 const Barcode& get_current_barcode() const;
475
490 const std::vector<Cycle>& get_representative_cycles();
498 const Cycle& get_representative_cycle(const Bar& bar);
499
523 bool vine_swap(Pos_index position);
524
525 private:
526 Underlying_matrix matrix_;
527 std::vector<Index> positionToIndex_;
528 Pos_index nextPosition_;
529 Index nextIndex_;
530};
531
532template <class Underlying_matrix, class Master_matrix>
534 Column_settings* colSettings)
535 : matrix_(colSettings), nextPosition_(0), nextIndex_(0)
536{}
537
538template <class Underlying_matrix, class Master_matrix>
539template <class Boundary_range>
541 const std::vector<Boundary_range>& orderedBoundaries, Column_settings* colSettings)
542 : matrix_(orderedBoundaries, colSettings),
543 positionToIndex_(orderedBoundaries.size()),
544 nextPosition_(orderedBoundaries.size()),
545 nextIndex_(orderedBoundaries.size())
546{
547 for (Index i = 0; i < orderedBoundaries.size(); i++) {
548 positionToIndex_[i] = i;
549 }
550}
551
552template <class Underlying_matrix, class Master_matrix>
554 unsigned int numberOfColumns, Column_settings* colSettings)
555 : matrix_(numberOfColumns, colSettings),
556 positionToIndex_(numberOfColumns),
557 nextPosition_(0),
558 nextIndex_(0)
559{}
560
561template <class Underlying_matrix, class Master_matrix>
562template <typename BirthComparatorFunction, typename DeathComparatorFunction>
564 Column_settings* colSettings,
565 const BirthComparatorFunction& birthComparator,
566 const DeathComparatorFunction& deathComparator)
567 : matrix_(colSettings, birthComparator, deathComparator), nextPosition_(0), nextIndex_(0)
568{}
569
570template <class Underlying_matrix, class Master_matrix>
571template <typename BirthComparatorFunction, typename DeathComparatorFunction, class Boundary_range>
573 const std::vector<Boundary_range>& orderedBoundaries,
574 Column_settings* colSettings,
575 const BirthComparatorFunction& birthComparator,
576 const DeathComparatorFunction& deathComparator)
577 : matrix_(orderedBoundaries, colSettings, birthComparator, deathComparator),
578 positionToIndex_(orderedBoundaries.size()),
579 nextPosition_(orderedBoundaries.size()),
580 nextIndex_(orderedBoundaries.size())
581{
582 for (Index i = 0; i < orderedBoundaries.size(); i++) {
583 positionToIndex_[i] = i;
584 }
585}
586
587template <class Underlying_matrix, class Master_matrix>
588template <typename BirthComparatorFunction, typename DeathComparatorFunction>
590 unsigned int numberOfColumns,
591 Column_settings* colSettings,
592 const BirthComparatorFunction& birthComparator,
593 const DeathComparatorFunction& deathComparator)
594 : matrix_(numberOfColumns, colSettings, birthComparator, deathComparator),
595 positionToIndex_(numberOfColumns),
596 nextPosition_(0),
597 nextIndex_(0)
598{}
599
600template <class Underlying_matrix, class Master_matrix>
602 const Position_to_index_overlay& matrixToCopy, Column_settings* colSettings)
603 : matrix_(matrixToCopy.matrix_, colSettings),
604 positionToIndex_(matrixToCopy.positionToIndex_),
605 nextPosition_(matrixToCopy.nextPosition_),
606 nextIndex_(matrixToCopy.nextIndex_)
607{}
608
609template <class Underlying_matrix, class Master_matrix>
611 Position_to_index_overlay&& other) noexcept
612 : matrix_(std::move(other.matrix_)),
613 positionToIndex_(std::move(other.positionToIndex_)),
614 nextPosition_(std::exchange(other.nextPosition_, 0)),
615 nextIndex_(std::exchange(other.nextIndex_, 0))
616{}
617
618template <class Underlying_matrix, class Master_matrix>
619template <class Boundary_range>
621 Dimension dim)
622{
623 if (positionToIndex_.size() <= nextPosition_) {
624 positionToIndex_.resize(nextPosition_ * 2 + 1);
625 }
626
627 positionToIndex_[nextPosition_++] = nextIndex_++;
628
629 matrix_.insert_boundary(boundary, dim);
630}
631
632template <class Underlying_matrix, class Master_matrix>
633template <class Boundary_range>
635 const Boundary_range& boundary,
636 Dimension dim)
637{
638 if (positionToIndex_.size() <= nextPosition_) {
639 positionToIndex_.resize(nextPosition_ * 2 + 1);
640 }
641
642 positionToIndex_[nextPosition_++] = nextIndex_++;
643
644 matrix_.insert_boundary(cellIndex, boundary, dim);
645}
646
647template <class Underlying_matrix, class Master_matrix>
650{
651 return matrix_.get_column(positionToIndex_[position]);
652}
653
654template <class Underlying_matrix, class Master_matrix>
657{
658 return matrix_.get_column(positionToIndex_[position]);
659}
660
661template <class Underlying_matrix, class Master_matrix>
664{
665 return matrix_.get_row(rowIndex);
666}
667
668template <class Underlying_matrix, class Master_matrix>
671{
672 return matrix_.get_row(rowIndex);
673}
674
675template <class Underlying_matrix, class Master_matrix>
677{
678 return matrix_.erase_empty_row(rowIndex);
679}
680
681template <class Underlying_matrix, class Master_matrix>
683{
684 --nextPosition_;
685
686 ID_index pivot = matrix_.get_pivot(positionToIndex_[position]);
687 std::vector<Index> columnsToSwap(nextPosition_ - position);
688
689 if (nextPosition_ != position) {
690 positionToIndex_[position] = positionToIndex_[position + 1];
691 for (Pos_index p = position + 1; p < nextPosition_; ++p) {
692 columnsToSwap[p - position - 1] = positionToIndex_[p];
693 positionToIndex_[p] = positionToIndex_[p + 1];
694 }
695 columnsToSwap.back() = positionToIndex_[nextPosition_];
696 }
697
698 matrix_.remove_maximal_cell(pivot, columnsToSwap);
699}
700
701template <class Underlying_matrix, class Master_matrix>
703{
704 --nextPosition_;
705 if constexpr (Master_matrix::Option_list::has_vine_update) {
706 std::vector<Index> columnsToSwap;
707 matrix_.remove_maximal_cell(matrix_.get_pivot(positionToIndex_[nextPosition_]), columnsToSwap);
708 } else {
709 matrix_.remove_last(); // linear with vine updates, so it is better to use remove_maximal_cell
710 }
711}
712
713template <class Underlying_matrix, class Master_matrix>
716{
717 return matrix_.get_max_dimension();
718}
719
720template <class Underlying_matrix, class Master_matrix>
723{
724 return matrix_.get_number_of_columns();
725}
726
727template <class Underlying_matrix, class Master_matrix>
730{
731 return matrix_.get_column_dimension(positionToIndex_[position]);
732}
733
734template <class Underlying_matrix, class Master_matrix>
736 Pos_index targetPosition)
737{
738 return matrix_.add_to(positionToIndex_[sourcePosition], positionToIndex_[targetPosition]);
739}
740
741template <class Underlying_matrix, class Master_matrix>
743 Pos_index sourcePosition, const Field_element& coefficient, Pos_index targetPosition)
744{
745 return matrix_.multiply_target_and_add_to(positionToIndex_[sourcePosition],
746 coefficient,
747 positionToIndex_[targetPosition]);
748}
749
750template <class Underlying_matrix, class Master_matrix>
752 const Field_element& coefficient, Pos_index sourcePosition, Pos_index targetPosition)
753{
754 return matrix_.multiply_source_and_add_to(coefficient,
755 positionToIndex_[sourcePosition],
756 positionToIndex_[targetPosition]);
757}
758
759template <class Underlying_matrix, class Master_matrix>
761 ID_index rowIndex) const
762{
763 return matrix_.is_zero_entry(positionToIndex_[position], rowIndex);
764}
765
766template <class Underlying_matrix, class Master_matrix>
768{
769 return matrix_.is_zero_column(positionToIndex_[position]);
770}
771
772template <class Underlying_matrix, class Master_matrix>
775{
776 Index id = matrix_.get_column_with_pivot(cellIndex);
777 Pos_index i = 0;
778 while (positionToIndex_[i] != id) ++i;
779 return i;
780}
781
782template <class Underlying_matrix, class Master_matrix>
785{
786 return matrix_.get_pivot(positionToIndex_[position]);
787}
788
789template <class Underlying_matrix, class Master_matrix>
792{
793 matrix_ = other.matrix_;
794 positionToIndex_ = other.positionToIndex_;
795 nextPosition_ = other.nextPosition_;
796 nextIndex_ = other.nextIndex_;
797
798 return *this;
799}
800
801template <class Underlying_matrix, class Master_matrix>
803{
804 return matrix_.print();
805}
806
807template <class Underlying_matrix, class Master_matrix>
810{
811 return matrix_.get_current_barcode();
812}
813
814template <class Underlying_matrix, class Master_matrix>
816{
817 matrix_.update_representative_cycles();
818}
819
820template <class Underlying_matrix, class Master_matrix>
821inline const std::vector<typename Position_to_index_overlay<Underlying_matrix, Master_matrix>::Cycle>&
823{
824 return matrix_.get_representative_cycles();
825}
826
827template <class Underlying_matrix, class Master_matrix>
830{
831 return matrix_.get_representative_cycle(bar);
832}
833
834template <class Underlying_matrix, class Master_matrix>
836{
837 Index next = matrix_.vine_swap_with_z_eq_1_case(positionToIndex_[position], positionToIndex_[position + 1]);
838 if (next == positionToIndex_[position]) {
839 std::swap(positionToIndex_[position], positionToIndex_[position + 1]);
840 return true;
841 }
842
843 return false;
844}
845
846template <class Underlying_matrix, class Master_matrix>
848{
849 Index next = matrix_.vine_swap(positionToIndex_[position], positionToIndex_[position + 1]);
850 if (next == positionToIndex_[position]) {
851 std::swap(positionToIndex_[position], positionToIndex_[position + 1]);
852 return true;
853 }
854
855 return false;
856}
857
858} // namespace persistence_matrix
859} // namespace Gudhi
860
861#endif // PM_POS_TO_ID_TRANSLATION_H
Overlay for chain matrices replacing all input and output MatIdx indices of the original methods with...
Definition: Position_to_index_overlay.h:40
bool is_zero_entry(Pos_index position, ID_index rowIndex) const
Indicates if the entry at given coordinates has value zero.
Definition: Position_to_index_overlay.h:760
typename Master_matrix::Index Index
Definition: Position_to_index_overlay.h:42
const std::vector< Cycle > & get_representative_cycles()
Only available if PersistenceMatrixOptions::can_retrieve_representative_cycles is true....
Definition: Position_to_index_overlay.h:822
friend void swap(Position_to_index_overlay &matrix1, Position_to_index_overlay &matrix2)
Swap operator.
Definition: Position_to_index_overlay.h:454
typename Master_matrix::Row Row
Definition: Position_to_index_overlay.h:54
Index get_number_of_columns() const
Returns the current number of columns in the matrix.
Definition: Position_to_index_overlay.h:722
typename Master_matrix::Entry_representative Entry_representative
Definition: Position_to_index_overlay.h:58
Dimension get_column_dimension(Pos_index position) const
Returns the dimension of the given cell.
Definition: Position_to_index_overlay.h:729
typename Master_matrix::Cycle Cycle
Definition: Position_to_index_overlay.h:57
const Cycle & get_representative_cycle(const Bar &bar)
Only available if PersistenceMatrixOptions::can_retrieve_representative_cycles is true....
Definition: Position_to_index_overlay.h:829
Dimension get_max_dimension() const
Returns the maximal dimension of a cell stored in the matrix. Only available if PersistenceMatrixOpti...
Definition: Position_to_index_overlay.h:715
typename Master_matrix::Field_operators Field_operators
Field operators class. Necessary only if PersistenceMatrixOptions::is_z2 is false.
Definition: Position_to_index_overlay.h:49
typename Master_matrix::Element Field_element
Definition: Position_to_index_overlay.h:50
void insert_boundary(const Boundary_range &boundary, Dimension dim=Master_matrix::template get_null_value< Dimension >())
Inserts at the end of the matrix a new ordered column corresponding to the given boundary....
Definition: Position_to_index_overlay.h:620
void erase_empty_row(ID_index rowIndex)
Only available if PersistenceMatrixOptions::has_row_access and PersistenceMatrixOptions::has_removabl...
Definition: Position_to_index_overlay.h:676
const Barcode & get_current_barcode() const
Returns the current barcode of the matrix. Available only if PersistenceMatrixOptions::has_column_pai...
Definition: Position_to_index_overlay.h:809
typename Master_matrix::Barcode Barcode
Definition: Position_to_index_overlay.h:56
bool is_zero_column(Pos_index position)
Indicates if the column at given index has value zero.
Definition: Position_to_index_overlay.h:767
void multiply_target_and_add_to(Pos_index sourcePosition, const Field_element &coefficient, Pos_index targetPosition)
Multiplies the target column with the coefficient and then adds the source column to it....
Definition: Position_to_index_overlay.h:742
void update_representative_cycles()
Only available if PersistenceMatrixOptions::can_retrieve_representative_cycles is true....
Definition: Position_to_index_overlay.h:815
typename Master_matrix::Pos_index Pos_index
Definition: Position_to_index_overlay.h:44
Position_to_index_overlay(Column_settings *colSettings)
Constructs an empty matrix.
Definition: Position_to_index_overlay.h:533
ID_index get_pivot(Pos_index position)
Returns the row index of the pivot of the given column.
Definition: Position_to_index_overlay.h:784
typename Master_matrix::ID_index ID_index
Definition: Position_to_index_overlay.h:43
void add_to(Pos_index sourcePosition, Pos_index targetPosition)
Adds column corresponding to sourcePosition onto the column corresponding to targetPosition.
Definition: Position_to_index_overlay.h:735
void remove_maximal_cell(Pos_index position)
Only available if PersistenceMatrixOptions::has_removable_columns, PersistenceMatrixOptions::has_vine...
Definition: Position_to_index_overlay.h:682
void reset(Column_settings *colSettings)
Resets the matrix to an empty matrix.
Definition: Position_to_index_overlay.h:438
typename Master_matrix::Column_settings Column_settings
Definition: Position_to_index_overlay.h:61
void remove_last()
Only available if PersistenceMatrixOptions::has_removable_columns is true and, if PersistenceMatrixOp...
Definition: Position_to_index_overlay.h:702
Row & get_row(ID_index rowIndex)
Only available if PersistenceMatrixOptions::has_row_access is true. Returns the row at the given row ...
Definition: Position_to_index_overlay.h:663
typename Master_matrix::Entry_constructor Entry_constructor
Definition: Position_to_index_overlay.h:59
typename Master_matrix::Bar Bar
Definition: Position_to_index_overlay.h:55
typename Master_matrix::Dimension Dimension
Definition: Position_to_index_overlay.h:45
typename Master_matrix::Column Column
Definition: Position_to_index_overlay.h:52
typename Master_matrix::Boundary Boundary
Definition: Position_to_index_overlay.h:51
Position_to_index_overlay & operator=(const Position_to_index_overlay &other)
Assign operator.
Definition: Position_to_index_overlay.h:791
void multiply_source_and_add_to(const Field_element &coefficient, Pos_index sourcePosition, Pos_index targetPosition)
Multiplies the source column with the coefficient before adding it to the target column....
Definition: Position_to_index_overlay.h:751
Column & get_column(Pos_index position)
Returns the column at the given PosIdx index. The type of the column depends on the chosen options,...
Definition: Position_to_index_overlay.h:649
Pos_index get_column_with_pivot(ID_index cellIndex) const
Returns the PosIdx index of the column which has the given row index as pivot. Assumes that the pivot...
Definition: Position_to_index_overlay.h:774
bool vine_swap_with_z_eq_1_case(Pos_index position)
Only available if PersistenceMatrixOptions::has_vine_update is true. Does the same than vine_swap,...
Definition: Position_to_index_overlay.h:835
bool vine_swap(Pos_index position)
Only available if PersistenceMatrixOptions::has_vine_update is true. Does a vine swap between two cel...
Definition: Position_to_index_overlay.h:847
Gudhi namespace.
Definition: SimplicialComplexForAlpha.h:14