lemon/bits/map_extender.h
author Peter Kovacs <kpeter@inf.elte.hu>
Fri, 03 Apr 2009 18:59:15 +0200
changeset 608 6ac5d9ae1d3d
parent 314 2cc60866a0c9
child 580 2313edd0db0b
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.
alpar@209
     1
/* -*- mode: C++; indent-tabs-mode: nil; -*-
deba@57
     2
 *
alpar@209
     3
 * This file is a part of LEMON, a generic C++ optimization library.
deba@57
     4
 *
alpar@440
     5
 * Copyright (C) 2003-2009
deba@57
     6
 * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
deba@57
     7
 * (Egervary Research Group on Combinatorial Optimization, EGRES).
deba@57
     8
 *
deba@57
     9
 * Permission to use, modify and distribute this software is granted
deba@57
    10
 * provided that this copyright notice appears in all copies. For
deba@57
    11
 * precise terms see the accompanying LICENSE file.
deba@57
    12
 *
deba@57
    13
 * This software is provided "AS IS" with no warranty of any kind,
deba@57
    14
 * express or implied, and with no claim as to its suitability for any
deba@57
    15
 * purpose.
deba@57
    16
 *
deba@57
    17
 */
deba@57
    18
deba@57
    19
#ifndef LEMON_BITS_MAP_EXTENDER_H
deba@57
    20
#define LEMON_BITS_MAP_EXTENDER_H
deba@57
    21
deba@57
    22
#include <iterator>
deba@57
    23
deba@57
    24
#include <lemon/bits/traits.h>
deba@57
    25
deba@57
    26
#include <lemon/concept_check.h>
deba@57
    27
#include <lemon/concepts/maps.h>
deba@57
    28
kpeter@314
    29
//\file
kpeter@314
    30
//\brief Extenders for iterable maps.
deba@57
    31
deba@57
    32
namespace lemon {
deba@57
    33
kpeter@314
    34
  // \ingroup graphbits
kpeter@314
    35
  //
kpeter@314
    36
  // \brief Extender for maps
deba@57
    37
  template <typename _Map>
deba@57
    38
  class MapExtender : public _Map {
deba@57
    39
  public:
deba@57
    40
deba@57
    41
    typedef _Map Parent;
deba@57
    42
    typedef MapExtender Map;
deba@57
    43
deba@57
    44
deba@57
    45
    typedef typename Parent::Graph Graph;
deba@57
    46
    typedef typename Parent::Key Item;
deba@57
    47
deba@57
    48
    typedef typename Parent::Key Key;
deba@57
    49
    typedef typename Parent::Value Value;
deba@57
    50
deba@57
    51
    class MapIt;
deba@57
    52
    class ConstMapIt;
deba@57
    53
deba@57
    54
    friend class MapIt;
deba@57
    55
    friend class ConstMapIt;
deba@57
    56
deba@57
    57
  public:
deba@57
    58
alpar@209
    59
    MapExtender(const Graph& graph)
deba@57
    60
      : Parent(graph) {}
deba@57
    61
alpar@209
    62
    MapExtender(const Graph& graph, const Value& value)
deba@57
    63
      : Parent(graph, value) {}
deba@57
    64
kpeter@263
    65
  private:
deba@57
    66
    MapExtender& operator=(const MapExtender& cmap) {
deba@57
    67
      return operator=<MapExtender>(cmap);
deba@57
    68
    }
deba@57
    69
deba@57
    70
    template <typename CMap>
deba@57
    71
    MapExtender& operator=(const CMap& cmap) {
deba@57
    72
      Parent::operator=(cmap);
deba@57
    73
      return *this;
alpar@209
    74
    }
deba@57
    75
kpeter@263
    76
  public:
deba@57
    77
    class MapIt : public Item {
deba@57
    78
    public:
alpar@209
    79
deba@57
    80
      typedef Item Parent;
deba@57
    81
      typedef typename Map::Value Value;
alpar@209
    82
deba@57
    83
      MapIt() {}
deba@57
    84
deba@57
    85
      MapIt(Invalid i) : Parent(i) { }
deba@57
    86
deba@57
    87
      explicit MapIt(Map& _map) : map(_map) {
deba@57
    88
        map.notifier()->first(*this);
deba@57
    89
      }
deba@57
    90
alpar@209
    91
      MapIt(const Map& _map, const Item& item)
alpar@209
    92
        : Parent(item), map(_map) {}
deba@57
    93
alpar@209
    94
      MapIt& operator++() {
alpar@209
    95
        map.notifier()->next(*this);
alpar@209
    96
        return *this;
deba@57
    97
      }
alpar@209
    98
deba@57
    99
      typename MapTraits<Map>::ConstReturnValue operator*() const {
alpar@209
   100
        return map[*this];
deba@57
   101
      }
deba@57
   102
deba@57
   103
      typename MapTraits<Map>::ReturnValue operator*() {
alpar@209
   104
        return map[*this];
deba@57
   105
      }
alpar@209
   106
deba@57
   107
      void set(const Value& value) {
alpar@209
   108
        map.set(*this, value);
deba@57
   109
      }
alpar@209
   110
deba@57
   111
    protected:
deba@57
   112
      Map& map;
alpar@209
   113
deba@57
   114
    };
deba@57
   115
deba@57
   116
    class ConstMapIt : public Item {
deba@57
   117
    public:
deba@57
   118
deba@57
   119
      typedef Item Parent;
deba@57
   120
deba@57
   121
      typedef typename Map::Value Value;
alpar@209
   122
deba@57
   123
      ConstMapIt() {}
deba@57
   124
deba@57
   125
      ConstMapIt(Invalid i) : Parent(i) { }
deba@57
   126
deba@57
   127
      explicit ConstMapIt(Map& _map) : map(_map) {
deba@57
   128
        map.notifier()->first(*this);
deba@57
   129
      }
deba@57
   130
alpar@209
   131
      ConstMapIt(const Map& _map, const Item& item)
alpar@209
   132
        : Parent(item), map(_map) {}
deba@57
   133
alpar@209
   134
      ConstMapIt& operator++() {
alpar@209
   135
        map.notifier()->next(*this);
alpar@209
   136
        return *this;
deba@57
   137
      }
deba@57
   138
deba@57
   139
      typename MapTraits<Map>::ConstReturnValue operator*() const {
alpar@209
   140
        return map[*this];
deba@57
   141
      }
deba@57
   142
deba@57
   143
    protected:
deba@57
   144
      const Map& map;
deba@57
   145
    };
deba@57
   146
deba@57
   147
    class ItemIt : public Item {
deba@57
   148
    public:
alpar@209
   149
deba@57
   150
      typedef Item Parent;
alpar@209
   151
deba@57
   152
      ItemIt() {}
deba@57
   153
deba@57
   154
      ItemIt(Invalid i) : Parent(i) { }
deba@57
   155
deba@57
   156
      explicit ItemIt(Map& _map) : map(_map) {
deba@57
   157
        map.notifier()->first(*this);
deba@57
   158
      }
deba@57
   159
alpar@209
   160
      ItemIt(const Map& _map, const Item& item)
alpar@209
   161
        : Parent(item), map(_map) {}
deba@57
   162
alpar@209
   163
      ItemIt& operator++() {
alpar@209
   164
        map.notifier()->next(*this);
alpar@209
   165
        return *this;
deba@57
   166
      }
deba@57
   167
deba@57
   168
    protected:
deba@57
   169
      const Map& map;
alpar@209
   170
deba@57
   171
    };
deba@57
   172
  };
deba@57
   173
kpeter@314
   174
  // \ingroup graphbits
kpeter@314
   175
  //
kpeter@314
   176
  // \brief Extender for maps which use a subset of the items.
deba@57
   177
  template <typename _Graph, typename _Map>
deba@57
   178
  class SubMapExtender : public _Map {
deba@57
   179
  public:
deba@57
   180
deba@57
   181
    typedef _Map Parent;
deba@57
   182
    typedef SubMapExtender Map;
deba@57
   183
deba@57
   184
    typedef _Graph Graph;
deba@57
   185
deba@57
   186
    typedef typename Parent::Key Item;
deba@57
   187
deba@57
   188
    typedef typename Parent::Key Key;
deba@57
   189
    typedef typename Parent::Value Value;
deba@57
   190
deba@57
   191
    class MapIt;
deba@57
   192
    class ConstMapIt;
deba@57
   193
deba@57
   194
    friend class MapIt;
deba@57
   195
    friend class ConstMapIt;
deba@57
   196
deba@57
   197
  public:
deba@57
   198
alpar@209
   199
    SubMapExtender(const Graph& _graph)
deba@57
   200
      : Parent(_graph), graph(_graph) {}
deba@57
   201
alpar@209
   202
    SubMapExtender(const Graph& _graph, const Value& _value)
deba@57
   203
      : Parent(_graph, _value), graph(_graph) {}
deba@57
   204
kpeter@263
   205
  private:
deba@57
   206
    SubMapExtender& operator=(const SubMapExtender& cmap) {
deba@57
   207
      return operator=<MapExtender>(cmap);
deba@57
   208
    }
deba@57
   209
deba@57
   210
    template <typename CMap>
deba@57
   211
    SubMapExtender& operator=(const CMap& cmap) {
deba@57
   212
      checkConcept<concepts::ReadMap<Key, Value>, CMap>();
deba@57
   213
      Item it;
deba@57
   214
      for (graph.first(it); it != INVALID; graph.next(it)) {
deba@57
   215
        Parent::set(it, cmap[it]);
deba@57
   216
      }
deba@57
   217
      return *this;
alpar@209
   218
    }
deba@57
   219
kpeter@263
   220
  public:
deba@57
   221
    class MapIt : public Item {
deba@57
   222
    public:
alpar@209
   223
deba@57
   224
      typedef Item Parent;
deba@57
   225
      typedef typename Map::Value Value;
alpar@209
   226
deba@57
   227
      MapIt() {}
deba@57
   228
deba@57
   229
      MapIt(Invalid i) : Parent(i) { }
deba@57
   230
deba@57
   231
      explicit MapIt(Map& _map) : map(_map) {
deba@57
   232
        map.graph.first(*this);
deba@57
   233
      }
deba@57
   234
alpar@209
   235
      MapIt(const Map& _map, const Item& item)
alpar@209
   236
        : Parent(item), map(_map) {}
deba@57
   237
alpar@209
   238
      MapIt& operator++() {
alpar@209
   239
        map.graph.next(*this);
alpar@209
   240
        return *this;
deba@57
   241
      }
alpar@209
   242
deba@57
   243
      typename MapTraits<Map>::ConstReturnValue operator*() const {
alpar@209
   244
        return map[*this];
deba@57
   245
      }
deba@57
   246
deba@57
   247
      typename MapTraits<Map>::ReturnValue operator*() {
alpar@209
   248
        return map[*this];
deba@57
   249
      }
alpar@209
   250
deba@57
   251
      void set(const Value& value) {
alpar@209
   252
        map.set(*this, value);
deba@57
   253
      }
alpar@209
   254
deba@57
   255
    protected:
deba@57
   256
      Map& map;
alpar@209
   257
deba@57
   258
    };
deba@57
   259
deba@57
   260
    class ConstMapIt : public Item {
deba@57
   261
    public:
deba@57
   262
deba@57
   263
      typedef Item Parent;
deba@57
   264
deba@57
   265
      typedef typename Map::Value Value;
alpar@209
   266
deba@57
   267
      ConstMapIt() {}
deba@57
   268
deba@57
   269
      ConstMapIt(Invalid i) : Parent(i) { }
deba@57
   270
deba@57
   271
      explicit ConstMapIt(Map& _map) : map(_map) {
deba@57
   272
        map.graph.first(*this);
deba@57
   273
      }
deba@57
   274
alpar@209
   275
      ConstMapIt(const Map& _map, const Item& item)
alpar@209
   276
        : Parent(item), map(_map) {}
deba@57
   277
alpar@209
   278
      ConstMapIt& operator++() {
alpar@209
   279
        map.graph.next(*this);
alpar@209
   280
        return *this;
deba@57
   281
      }
deba@57
   282
deba@57
   283
      typename MapTraits<Map>::ConstReturnValue operator*() const {
alpar@209
   284
        return map[*this];
deba@57
   285
      }
deba@57
   286
deba@57
   287
    protected:
deba@57
   288
      const Map& map;
deba@57
   289
    };
deba@57
   290
deba@57
   291
    class ItemIt : public Item {
deba@57
   292
    public:
alpar@209
   293
deba@57
   294
      typedef Item Parent;
alpar@209
   295
deba@57
   296
      ItemIt() {}
deba@57
   297
deba@57
   298
      ItemIt(Invalid i) : Parent(i) { }
deba@57
   299
deba@57
   300
      explicit ItemIt(Map& _map) : map(_map) {
deba@57
   301
        map.graph.first(*this);
deba@57
   302
      }
deba@57
   303
alpar@209
   304
      ItemIt(const Map& _map, const Item& item)
alpar@209
   305
        : Parent(item), map(_map) {}
deba@57
   306
alpar@209
   307
      ItemIt& operator++() {
alpar@209
   308
        map.graph.next(*this);
alpar@209
   309
        return *this;
deba@57
   310
      }
deba@57
   311
deba@57
   312
    protected:
deba@57
   313
      const Map& map;
alpar@209
   314
deba@57
   315
    };
alpar@209
   316
deba@57
   317
  private:
deba@57
   318
deba@57
   319
    const Graph& graph;
alpar@209
   320
deba@57
   321
  };
deba@57
   322
deba@57
   323
}
deba@57
   324
deba@57
   325
#endif