examples/rips/rips.cpp
author Dmitriy Morozov <dmitriy@mrzv.org>
Mon Jul 25 23:21:29 2011 -0700 (10 months ago)
branchdev
changeset 244 66235db8d8b7
parent 1250a2c2283e4a8
permissions -rw-r--r--
Added cohomology/candidates counter to i/t/cohomology-persistence.hpp
dmitriy@92
     1
#include <topology/rips.h>
dmitriy@113
     2
#include <topology/filtration.h>
dmitriy@113
     3
#include <topology/static-persistence.h>
dmitriy@115
     4
#include <topology/dynamic-persistence.h>
dmitriy@113
     5
#include <topology/persistence-diagram.h>
dmitriy@113
     6
#include <utilities/containers.h>           // for BackInsertFunctor
dmitriy@113
     7
dmitriy@113
     8
#include <fstream>
dmitriy@113
     9
#include <boost/archive/binary_oarchive.hpp>
dmitriy@113
    10
#include <boost/serialization/map.hpp>
dmitriy@92
    11
dmitriy@109
    12
// Trivial example of size() points on a line with integer coordinates
dmitriy@92
    13
struct Distances
dmitriy@92
    14
{
dmitriy@92
    15
    typedef         int             IndexType;
dmitriy@92
    16
    typedef         double          DistanceType;
dmitriy@92
    17
dmitriy@92
    18
    DistanceType    operator()(IndexType a, IndexType b) const      { return std::abs(a - b); }
dmitriy@92
    19
dmitriy@92
    20
    size_t          size() const                                    { return 2000; }
dmitriy@92
    21
    IndexType       begin() const                                   { return 0; }
dmitriy@92
    22
    IndexType       end() const                                     { return size(); }
dmitriy@92
    23
};
dmitriy@92
    24
dmitriy@113
    25
//typedef         Rips<ExplicitDistances<Distances> >                   Generator;
dmitriy@113
    26
typedef         Rips<Distances>                                         Generator;
dmitriy@113
    27
typedef         Generator::Simplex                                      Smplx;
dmitriy@179
    28
typedef         Filtration<Smplx>                                       Fltr;
dmitriy@179
    29
typedef         StaticPersistence<>                                     Persistence;
dmitriy@179
    30
// typedef         DynamicPersistenceChains<>                              Persistence;
dmitriy@115
    31
typedef         PersistenceDiagram<>                                    PDgm;
dmitriy@113
    32
dmitriy@113
    33
dmitriy@92
    34
int main(int argc, char* argv[])
dmitriy@92
    35
{
dmitriy@92
    36
#ifdef LOGGING
dmitriy@92
    37
	rlog::RLogInit(argc, argv);
dmitriy@92
    38
dmitriy@92
    39
	stdoutLog.subscribeTo( RLOG_CHANNEL("error") );
dmitriy@113
    40
	stdoutLog.subscribeTo( RLOG_CHANNEL("info") );
dmitriy@113
    41
	//stdoutLog.subscribeTo( RLOG_CHANNEL("rips/info") );
dmitriy@113
    42
	//stdoutLog.subscribeTo( RLOG_CHANNEL("rips/debug") );
dmitriy@92
    43
#endif
dmitriy@92
    44
dmitriy@92
    45
    Distances distances;
morozov@94
    46
    
dmitriy@109
    47
    // Storing ExplicitDistances speeds up the computation (at the price of memory)
dmitriy@113
    48
    //ExplicitDistances<Distances> explicit_distances(distances);
dmitriy@92
    49
dmitriy@113
    50
    Generator               rips(distances);
dmitriy@113
    51
    Generator::Evaluator    size(distances);
dmitriy@179
    52
    Fltr                    f;
dmitriy@92
    53
    
dmitriy@113
    54
    // Generate 2-skeleton of the Rips complex for epsilon = 50
dmitriy@179
    55
    rips.generate(2, 10, make_push_back_functor(f));
dmitriy@179
    56
    rInfo("Generated complex of size: %d",  f.size());
dmitriy@113
    57
dmitriy@113
    58
    // Generate filtration with respect to distance and compute its persistence
dmitriy@179
    59
    f.sort(Generator::Comparison(distances));
dmitriy@113
    60
    Persistence p(f);
dmitriy@113
    61
    p.pair_simplices();
dmitriy@113
    62
    rInfo("Simplices paired");
dmitriy@113
    63
dmitriy@179
    64
    Persistence::SimplexMap<Fltr>   m = p.make_simplex_map(f);
dmitriy@179
    65
dmitriy@113
    66
    // Record the persistence intervals in the persistence diagrams
dmitriy@113
    67
    std::map<Dimension, PDgm> dgms;
dmitriy@113
    68
    init_diagrams(dgms, p.begin(), p.end(), 
dmitriy@179
    69
                  evaluate_through_map(m, size), 
dmitriy@179
    70
                  evaluate_through_map(m, Smplx::DimensionExtractor()));
dmitriy@113
    71
dmitriy@113
    72
    // Serialize the diagrams to a file
dmitriy@113
    73
    std::ofstream ofs("rips-diagrams");
dmitriy@113
    74
    boost::archive::binary_oarchive oa(ofs);
dmitriy@113
    75
    oa << dgms;
dmitriy@115
    76
dmitriy@115
    77
    // Output cycles
dmitriy@179
    78
    for (Persistence::iterator cur = p.begin(); cur != p.end(); ++cur)
dmitriy@115
    79
    {
dmitriy@179
    80
        const Persistence::Cycle& cycle = cur->cycle;
dmitriy@115
    81
dmitriy@115
    82
        if (!cur->sign())        // only negative simplices have non-empty cycles
dmitriy@115
    83
        {
dmitriy@115
    84
            Persistence::OrderIndex birth = cur->pair;      // the cycle that cur killed was born when we added birth (another simplex)
dmitriy@115
    85
dmitriy@179
    86
            const Smplx& b = m[birth];
dmitriy@179
    87
            const Smplx& d = m[cur];
dmitriy@115
    88
            
dmitriy@115
    89
            if (b.dimension() != 1) continue;
dmitriy@115
    90
            std::cout << "Pair: (" << size(b) << ", " << size(d) << ")" << std::endl;
dmitriy@179
    91
        } else if (cur->unpaired())    // positive could be unpaired
dmitriy@115
    92
        {
dmitriy@179
    93
            const Smplx& b = m[cur];
dmitriy@115
    94
            if (b.dimension() != 1) continue;
dmitriy@115
    95
            
dmitriy@115
    96
            std::cout << "Unpaired birth: " << size(b) << std::endl;
dmitriy@179
    97
            // cycle = cur->chain;
dmitriy@115
    98
        }
dmitriy@115
    99
dmitriy@115
   100
        // Iterate over the cycle
dmitriy@179
   101
        for (Persistence::Cycle::const_iterator si =  cycle.begin(); si != cycle.end(); ++si)
dmitriy@115
   102
        {
dmitriy@179
   103
            const Smplx& s = m[*si];
dmitriy@115
   104
            //std::cout << s.dimension() << std::endl;
dmitriy@115
   105
            const Smplx::VertexContainer& vertices = s.vertices();          // std::vector<Vertex> where Vertex = Distances::IndexType
dmitriy@115
   106
            AssertMsg(vertices.size() == s.dimension() + 1, "dimension of a simplex is one less than the number of its vertices");
dmitriy@115
   107
            std::cout << vertices[0] << " " << vertices[1] << std::endl;
dmitriy@115
   108
        }
dmitriy@115
   109
    }
dmitriy@92
   110
}