lemon/bits/vector_map.h
author Peter Kovacs <kpeter@inf.elte.hu>
Fri, 03 Apr 2009 18:59:15 +0200
changeset 600 6ac5d9ae1d3d
parent 440 88ed40ad0d4f
child 609 4137ef9aacc6
permissions -rw-r--r--
Support real types + numerical stability fix in NS (#254)

- Real types are supported by appropriate inicialization.
- A feature of the XTI spanning tree structure is removed to ensure
numerical stability (could cause problems using integer types).
The node potentials are updated always on the lower subtree,
in order to prevent overflow problems.
The former method isn't notably faster during to our tests.
     1 /* -*- mode: C++; indent-tabs-mode: nil; -*-
     2  *
     3  * This file is a part of LEMON, a generic C++ optimization library.
     4  *
     5  * Copyright (C) 2003-2009
     6  * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
     7  * (Egervary Research Group on Combinatorial Optimization, EGRES).
     8  *
     9  * Permission to use, modify and distribute this software is granted
    10  * provided that this copyright notice appears in all copies. For
    11  * precise terms see the accompanying LICENSE file.
    12  *
    13  * This software is provided "AS IS" with no warranty of any kind,
    14  * express or implied, and with no claim as to its suitability for any
    15  * purpose.
    16  *
    17  */
    18 
    19 #ifndef LEMON_BITS_VECTOR_MAP_H
    20 #define LEMON_BITS_VECTOR_MAP_H
    21 
    22 #include <vector>
    23 #include <algorithm>
    24 
    25 #include <lemon/core.h>
    26 #include <lemon/bits/alteration_notifier.h>
    27 
    28 #include <lemon/concept_check.h>
    29 #include <lemon/concepts/maps.h>
    30 
    31 //\ingroup graphbits
    32 //
    33 //\file
    34 //\brief Vector based graph maps.
    35 namespace lemon {
    36 
    37   // \ingroup graphbits
    38   //
    39   // \brief Graph map based on the std::vector storage.
    40   //
    41   // The VectorMap template class is graph map structure that automatically
    42   // updates the map when a key is added to or erased from the graph.
    43   // This map type uses std::vector to store the values.
    44   //
    45   // \tparam _Graph The graph this map is attached to.
    46   // \tparam _Item The item type of the graph items.
    47   // \tparam _Value The value type of the map.
    48   template <typename _Graph, typename _Item, typename _Value>
    49   class VectorMap
    50     : public ItemSetTraits<_Graph, _Item>::ItemNotifier::ObserverBase {
    51   private:
    52 
    53     // The container type of the map.
    54     typedef std::vector<_Value> Container;
    55 
    56   public:
    57 
    58     // The graph type of the map.
    59     typedef _Graph Graph;
    60     // The item type of the map.
    61     typedef _Item Item;
    62     // The reference map tag.
    63     typedef True ReferenceMapTag;
    64 
    65     // The key type of the map.
    66     typedef _Item Key;
    67     // The value type of the map.
    68     typedef _Value Value;
    69 
    70     // The notifier type.
    71     typedef typename ItemSetTraits<_Graph, _Item>::ItemNotifier Notifier;
    72 
    73     // The map type.
    74     typedef VectorMap Map;
    75     // The base class of the map.
    76     typedef typename Notifier::ObserverBase Parent;
    77 
    78     // The reference type of the map;
    79     typedef typename Container::reference Reference;
    80     // The const reference type of the map;
    81     typedef typename Container::const_reference ConstReference;
    82 
    83 
    84     // \brief Constructor to attach the new map into the notifier.
    85     //
    86     // It constructs a map and attachs it into the notifier.
    87     // It adds all the items of the graph to the map.
    88     VectorMap(const Graph& graph) {
    89       Parent::attach(graph.notifier(Item()));
    90       container.resize(Parent::notifier()->maxId() + 1);
    91     }
    92 
    93     // \brief Constructor uses given value to initialize the map.
    94     //
    95     // It constructs a map uses a given value to initialize the map.
    96     // It adds all the items of the graph to the map.
    97     VectorMap(const Graph& graph, const Value& value) {
    98       Parent::attach(graph.notifier(Item()));
    99       container.resize(Parent::notifier()->maxId() + 1, value);
   100     }
   101 
   102   private:
   103     // \brief Copy constructor
   104     //
   105     // Copy constructor.
   106     VectorMap(const VectorMap& _copy) : Parent() {
   107       if (_copy.attached()) {
   108         Parent::attach(*_copy.notifier());
   109         container = _copy.container;
   110       }
   111     }
   112 
   113     // \brief Assign operator.
   114     //
   115     // This operator assigns for each item in the map the
   116     // value mapped to the same item in the copied map.
   117     // The parameter map should be indiced with the same
   118     // itemset because this assign operator does not change
   119     // the container of the map.
   120     VectorMap& operator=(const VectorMap& cmap) {
   121       return operator=<VectorMap>(cmap);
   122     }
   123 
   124 
   125     // \brief Template assign operator.
   126     //
   127     // The given parameter should conform to the ReadMap
   128     // concecpt and could be indiced by the current item set of
   129     // the NodeMap. In this case the value for each item
   130     // is assigned by the value of the given ReadMap.
   131     template <typename CMap>
   132     VectorMap& operator=(const CMap& cmap) {
   133       checkConcept<concepts::ReadMap<Key, _Value>, CMap>();
   134       const typename Parent::Notifier* nf = Parent::notifier();
   135       Item it;
   136       for (nf->first(it); it != INVALID; nf->next(it)) {
   137         set(it, cmap[it]);
   138       }
   139       return *this;
   140     }
   141 
   142   public:
   143 
   144     // \brief The subcript operator.
   145     //
   146     // The subscript operator. The map can be subscripted by the
   147     // actual items of the graph.
   148     Reference operator[](const Key& key) {
   149       return container[Parent::notifier()->id(key)];
   150     }
   151 
   152     // \brief The const subcript operator.
   153     //
   154     // The const subscript operator. The map can be subscripted by the
   155     // actual items of the graph.
   156     ConstReference operator[](const Key& key) const {
   157       return container[Parent::notifier()->id(key)];
   158     }
   159 
   160 
   161     // \brief The setter function of the map.
   162     //
   163     // It the same as operator[](key) = value expression.
   164     void set(const Key& key, const Value& value) {
   165       (*this)[key] = value;
   166     }
   167 
   168   protected:
   169 
   170     // \brief Adds a new key to the map.
   171     //
   172     // It adds a new key to the map. It is called by the observer notifier
   173     // and it overrides the add() member function of the observer base.
   174     virtual void add(const Key& key) {
   175       int id = Parent::notifier()->id(key);
   176       if (id >= int(container.size())) {
   177         container.resize(id + 1);
   178       }
   179     }
   180 
   181     // \brief Adds more new keys to the map.
   182     //
   183     // It adds more new keys to the map. It is called by the observer notifier
   184     // and it overrides the add() member function of the observer base.
   185     virtual void add(const std::vector<Key>& keys) {
   186       int max = container.size() - 1;
   187       for (int i = 0; i < int(keys.size()); ++i) {
   188         int id = Parent::notifier()->id(keys[i]);
   189         if (id >= max) {
   190           max = id;
   191         }
   192       }
   193       container.resize(max + 1);
   194     }
   195 
   196     // \brief Erase a key from the map.
   197     //
   198     // Erase a key from the map. It is called by the observer notifier
   199     // and it overrides the erase() member function of the observer base.
   200     virtual void erase(const Key& key) {
   201       container[Parent::notifier()->id(key)] = Value();
   202     }
   203 
   204     // \brief Erase more keys from the map.
   205     //
   206     // It erases more keys from the map. It is called by the observer notifier
   207     // and it overrides the erase() member function of the observer base.
   208     virtual void erase(const std::vector<Key>& keys) {
   209       for (int i = 0; i < int(keys.size()); ++i) {
   210         container[Parent::notifier()->id(keys[i])] = Value();
   211       }
   212     }
   213 
   214     // \brief Build the map.
   215     //
   216     // It builds the map. It is called by the observer notifier
   217     // and it overrides the build() member function of the observer base.
   218     virtual void build() {
   219       int size = Parent::notifier()->maxId() + 1;
   220       container.reserve(size);
   221       container.resize(size);
   222     }
   223 
   224     // \brief Clear the map.
   225     //
   226     // It erases all items from the map. It is called by the observer notifier
   227     // and it overrides the clear() member function of the observer base.
   228     virtual void clear() {
   229       container.clear();
   230     }
   231 
   232   private:
   233 
   234     Container container;
   235 
   236   };
   237 
   238 }
   239 
   240 #endif