include/topology/vineyard.h
author Dmitriy Morozov <morozov@cs.duke.edu>
Wed, 27 Feb 2008 07:57:45 -0500
branchar
changeset 76 66622c6bf8cf
parent 61 f905b57dd7ab
child 77 8e55bf20802a
permissions -rw-r--r--
Merged upstream changes (to get boost::program_options setup in CMake)

/*
 * Author: Dmitriy Morozov
 * Department of Computer Science, Duke University, 2005 -- 2006
 */

#ifndef __VINEYARD_H__
#define __VINEYARD_H__

#include "utilities/types.h"
#include <list>
#include <string>

#include <boost/serialization/access.hpp>
#include <boost/serialization/vector.hpp>
#include <boost/serialization/nvp.hpp>
#include <boost/serialization/list.hpp>
#include <boost/serialization/is_abstract.hpp>
	

template<class Smplx>	class Knee;
template<class Smplx>	class Vine;

/**
 * Vineyard class. Keeps track of vines and knees. switched() is the key function called
 * by filtration when pairing switches after a Filtration::transpose().
 *
 * \ingroup topology
 */
template<class FltrSmplx>
class Vineyard
{
	public:
		typedef							FltrSmplx									FiltrationSimplex;
		typedef							typename FiltrationSimplex::Simplex			Simplex;
		typedef							Vine<Simplex>								Vine;
		typedef							Knee<Simplex>								Knee;
		typedef							std::list<Vine>								VineList;
		typedef							std::vector<VineList>						VineListVector;
		typedef							typename FiltrationSimplex::Cycle			Cycle;

		typedef							typename FiltrationSimplex::Index			Index;
		typedef							typename FiltrationSimplex::Evaluator		Evaluator;
										
	public:
										Vineyard(Evaluator* eval = 0): 
											evaluator(eval)							{}

		void							start_vines(Index bg, Index end);
		void							switched(Index i, Index j);
		void							record_diagram(Index bg, Index end);

		void							set_evaluator(Evaluator* eval)				{ evaluator = eval; }

		void							save_edges(const std::string& filename) const;

	protected:
		typename Knee::SimplexList  	resolve_cycle(Index i) const;

	private:
		void							record_knee(Index i);
		void							start_vine(Index i);

	private:
		VineListVector					vines;
		Evaluator*						evaluator;
};

/**
 * Knee class stores the knee in R^3 as well as the cycle that is associated with the Simplex starting from the Knee.
 *
 * \ingroup topology
 */
template<class S>
class Knee
{
	public:
		typedef					S												Simplex;
		typedef					std::list<Simplex>								SimplexList;
	
		RealType				birth;
		RealType				death;
		RealType				time;
		SimplexList				cycle;
			
								// Default parameters for serialization
								Knee(RealType b = 0, RealType d = 0, RealType t = 0):
									birth(b), death(d), time(t)
								{}
								Knee(const Knee& other): 
									birth(other.birth), death(other.death), time(other.time)
								{}

		bool 					is_diagonal() const								{ return birth == death; }
		bool					is_infinite() const								{ return (death == Infinity) || (birth == Infinity); }
		void 					set_cycle(const SimplexList& lst)				{ cycle = lst; }

		std::ostream&			operator<<(std::ostream& out) const				{ return out << "(" << birth << ", " 
																									<< death << ", " 
																									<< time  << ")"; }
	
	private:
		friend class boost::serialization::access;

		template<class Archive>
		void 					serialize(Archive& ar, version_type );
};

template<class S>
std::ostream& operator<<(std::ostream& out, const Knee<S>& k) 					{ return k.operator<<(out); }

/**
 * Vine is a list of Knees
 */
template<class S>
class Vine: public std::list<Knee<S> >
{	
	public:
		typedef					S												Simplex;
		typedef					Knee<Simplex>									Knee;
		typedef					std::list<Knee>									VineRepresentation;
		typedef					typename VineRepresentation::const_iterator		const_knee_iterator;
		
								Vine()											{}
								Vine(const Knee& k)								{ add(k); }
		
		void 					add(RealType b, RealType d, RealType t)			{ push_back(Knee(b,d,t)); }
		void 					add(const Knee& k)								{ push_back(k); }

		using VineRepresentation::begin;
		using VineRepresentation::end;
		using VineRepresentation::front;
		using VineRepresentation::back;
		using VineRepresentation::size;
		using VineRepresentation::empty;

	protected:
		using VineRepresentation::push_back;

	private:
		friend class boost::serialization::access;

		template<class Archive>
		void 					serialize(Archive& ar, version_type );
};


#include "vineyard.hpp"

#endif // __VINEYARD_H__