include/utilities/property-maps.h
author Christos Mantoulidis <cmad@stanford.edu>
Tue, 04 Aug 2009 16:58:44 -0700
branchdev
changeset 157 700cbac5b23c
parent 97 0a9bd3f34419
child 179 d15c6d144645
permissions -rw-r--r--
Modified cohomology code (unweighted and weighted) so that it doesn't use std::map for boundary computations, which should optimize memory usage.

#ifndef __PROPERTY_MAPS_H__
#define __PROPERTY_MAPS_H__

#include <boost/property_map.hpp>
#include <boost/iterator/iterator_traits.hpp>
#include <algorithm>
#include "utilities/log.h"


/* Associative Map */           // FIXME: this needs to have more thought put into it
template<class UniquePairAssociativeContainer_>
class AssociativeMap: public boost::associative_property_map<UniquePairAssociativeContainer_>
{
    public:
        typedef         boost::associative_property_map<UniquePairAssociativeContainer_>        Parent;
        
    public:
        // FIXME: takes begin, end, and initializes with the reverse
        AssociativeMap():
            container(), Parent(container)                                                      {}

    private:
        UniquePairAssociativeContainer_                                                         container;
};


/* Dereference Map */
template<class Iterator_>
class DereferenceMap
{
    public:
        typedef         Iterator_                                                               Iterator;
        typedef         Iterator                                                                key_type;
        typedef         typename boost::iterator_value<Iterator>::type                          value_type;
        typedef         boost::readable_property_map_tag                                        category;

    public:
        value_type      operator[](const key_type& k) const                                     { return *k; }
};


/* Binary Search Map */
template<class Query_, class Index_, class Comparison_ = std::less<Query_> >
class BinarySearchMap
{
    public:
        typedef         Query_                                                                  Query;
        typedef         Index_                                                                  Index;
        typedef         Comparison_                                                             Comparison;

        typedef         Query                                                                   key_type;
        typedef         Index                                                                   value_type;
        typedef         boost::readable_property_map_tag                                        category;

   public:
                        BinarySearchMap(Index bg, Index end, 
                                        Comparison cmp = Comparison()): 
                            bg_(bg), end_(end), cmp_(cmp)                                       {}

        value_type      operator[](const key_type& k) const                                     
        { 
            value_type res = std::lower_bound(bg_, end_, k, cmp_);
            AssertMsg(!cmp_(*res, k) && !cmp_(k, *res), "Query must always be found");
            return res;
        }

   private:
        Index           bg_;
        Index           end_;
        Comparison      cmp_;

};

/* Offset Map */
template<class From_, class To_>
struct OffsetMap
{
    typedef             From_                                                   From;
    typedef             To_                                                     To;
    typedef             From                                                    key_type;
    typedef             To                                                      value_type;

                        OffsetMap(From bg_from, To bg_to):
                            bg_from_(bg_from), bg_to_(bg_to)                    {}
                        
    To                  operator[](From i) const                                { return bg_to_ + (i - bg_from_); }

    From                from() const                                            { return bg_from_; }
    To                  to() const                                              { return bg_to_; }
    
    
    template<class NewFrom_> struct rebind_from
    { typedef           OffsetMap<NewFrom_, To_>                                other; };
    template<class NewTo_> struct rebind_to
    { typedef           OffsetMap<From_, NewTo_>                                other; };


    private:
                        From                                                    bg_from_;
                        To                                                      bg_to_;
};

template<class From_, class To_>
OffsetMap<From_, To_>
make_offset_map(From_ bg_from, To_ bg_to)
{ return OffsetMap<From_, To_>(bg_from, bg_to); }


/* ThroughMap */
template<class Functor_, class Map_>
class ThroughMap
{
    public:
        typedef                 Map_                                            Map;
        typedef                 Functor_                                        Functor;

        typedef                 typename Functor::result_type                   result_type;
        typedef                 typename Map::key_type                          first_argument_type;

                                ThroughMap(const Map&       map,
                                           const Functor&   functor):
                                    map_(map),
                                    functor_(functor)                           {}

        result_type             operator()(first_argument_type a) const         { return functor_(map_[a]); }

    private:
        const Map&              map_;
        const Functor&          functor_;
};

template<class Map, class Functor>
ThroughMap<Functor, Map>
evaluate_through_map(const Map& map, const Functor& functor)
{ return ThroughMap<Functor, Map>(map, functor); }

#endif // __PROPERTY_MAPS_H__