↑ Collapse diff ↑
Show white space 128 line context
1
prefix=@CMAKE_INSTALL_PREFIX@
2
exec_prefix=@CMAKE_INSTALL_PREFIX@/bin
3
libdir=@CMAKE_INSTALL_PREFIX@/lib
4
includedir=@CMAKE_INSTALL_PREFIX@/include
5

	
6
Name: @PROJECT_NAME@
7
Description: Library for Efficient Modeling and Optimization in Networks
8
Version: @PROJECT_VERSION@
9
Libs: -L${libdir} -lemon @GLPK_LIBS@ @CPLEX_LIBS@ @SOPLEX_LIBS@ @CLP_LIBS@ @CBC_LIBS@
10
Cflags: -I${includedir}
Show white space 128 line context
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-2010
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_NAGAMOCHI_IBARAKI_H
20
#define LEMON_NAGAMOCHI_IBARAKI_H
21

	
22

	
23
/// \ingroup min_cut
24
/// \file
25
/// \brief Implementation of the Nagamochi-Ibaraki algorithm.
26

	
27
#include <lemon/core.h>
28
#include <lemon/bin_heap.h>
29
#include <lemon/bucket_heap.h>
30
#include <lemon/maps.h>
31
#include <lemon/radix_sort.h>
32
#include <lemon/unionfind.h>
33

	
34
#include <cassert>
35

	
36
namespace lemon {
37

	
38
  /// \brief Default traits class for NagamochiIbaraki class.
39
  ///
40
  /// Default traits class for NagamochiIbaraki class.
41
  /// \param GR The undirected graph type.
42
  /// \param CM Type of capacity map.
43
  template <typename GR, typename CM>
44
  struct NagamochiIbarakiDefaultTraits {
45
    /// The type of the capacity map.
46
    typedef typename CM::Value Value;
47

	
48
    /// The undirected graph type the algorithm runs on.
49
    typedef GR Graph;
50

	
51
    /// \brief The type of the map that stores the edge capacities.
52
    ///
53
    /// The type of the map that stores the edge capacities.
54
    /// It must meet the \ref concepts::ReadMap "ReadMap" concept.
55
    typedef CM CapacityMap;
56

	
57
    /// \brief Instantiates a CapacityMap.
58
    ///
59
    /// This function instantiates a \ref CapacityMap.
60
#ifdef DOXYGEN
61
    static CapacityMap *createCapacityMap(const Graph& graph)
62
#else
63
    static CapacityMap *createCapacityMap(const Graph&)
64
#endif
65
    {
66
        LEMON_ASSERT(false, "CapacityMap is not initialized");
67
        return 0; // ignore warnings
68
    }
69

	
70
    /// \brief The cross reference type used by heap.
71
    ///
72
    /// The cross reference type used by heap.
73
    /// Usually \c Graph::NodeMap<int>.
74
    typedef typename Graph::template NodeMap<int> HeapCrossRef;
75

	
76
    /// \brief Instantiates a HeapCrossRef.
77
    ///
78
    /// This function instantiates a \ref HeapCrossRef.
79
    /// \param g is the graph, to which we would like to define the
80
    /// \ref HeapCrossRef.
81
    static HeapCrossRef *createHeapCrossRef(const Graph& g) {
82
      return new HeapCrossRef(g);
83
    }
84

	
85
    /// \brief The heap type used by NagamochiIbaraki algorithm.
86
    ///
87
    /// The heap type used by NagamochiIbaraki algorithm. It has to
88
    /// maximize the priorities.
89
    ///
90
    /// \sa BinHeap
91
    /// \sa NagamochiIbaraki
92
    typedef BinHeap<Value, HeapCrossRef, std::greater<Value> > Heap;
93

	
94
    /// \brief Instantiates a Heap.
95
    ///
96
    /// This function instantiates a \ref Heap.
97
    /// \param r is the cross reference of the heap.
98
    static Heap *createHeap(HeapCrossRef& r) {
99
      return new Heap(r);
100
    }
101
  };
102

	
103
  /// \ingroup min_cut
104
  ///
105
  /// \brief Calculates the minimum cut in an undirected graph.
106
  ///
107
  /// Calculates the minimum cut in an undirected graph with the
108
  /// Nagamochi-Ibaraki algorithm. The algorithm separates the graph's
109
  /// nodes into two partitions with the minimum sum of edge capacities
110
  /// between the two partitions. The algorithm can be used to test
111
  /// the network reliability, especially to test how many links have
112
  /// to be destroyed in the network to split it to at least two
113
  /// distinict subnetworks.
114
  ///
115
  /// The complexity of the algorithm is \f$ O(nm\log(n)) \f$ but with
116
  /// \ref FibHeap "Fibonacci heap" it can be decreased to
117
  /// \f$ O(nm+n^2\log(n)) \f$.  When the edges have unit capacities,
118
  /// \c BucketHeap can be used which yields \f$ O(nm) \f$ time
119
  /// complexity.
120
  ///
121
  /// \warning The value type of the capacity map should be able to
122
  /// hold any cut value of the graph, otherwise the result can
123
  /// overflow.
124
  /// \note This capacity is supposed to be integer type.
125
#ifdef DOXYGEN
126
  template <typename GR, typename CM, typename TR>
127
#else
128
  template <typename GR,
129
            typename CM = typename GR::template EdgeMap<int>,
130
            typename TR = NagamochiIbarakiDefaultTraits<GR, CM> >
131
#endif
132
  class NagamochiIbaraki {
133
  public:
134

	
135
    typedef TR Traits;
136
    /// The type of the underlying graph.
137
    typedef typename Traits::Graph Graph;
138

	
139
    /// The type of the capacity map.
140
    typedef typename Traits::CapacityMap CapacityMap;
141
    /// The value type of the capacity map.
142
    typedef typename Traits::CapacityMap::Value Value;
143

	
144
    /// The heap type used by the algorithm.
145
    typedef typename Traits::Heap Heap;
146
    /// The cross reference type used for the heap.
147
    typedef typename Traits::HeapCrossRef HeapCrossRef;
148

	
149
    ///\name Named template parameters
150

	
151
    ///@{
152

	
153
    struct SetUnitCapacityTraits : public Traits {
154
      typedef ConstMap<typename Graph::Edge, Const<int, 1> > CapacityMap;
155
      static CapacityMap *createCapacityMap(const Graph&) {
156
        return new CapacityMap();
157
      }
158
    };
159

	
160
    /// \brief \ref named-templ-param "Named parameter" for setting
161
    /// the capacity map to a constMap<Edge, int, 1>() instance
162
    ///
163
    /// \ref named-templ-param "Named parameter" for setting
164
    /// the capacity map to a constMap<Edge, int, 1>() instance
165
    struct SetUnitCapacity
166
      : public NagamochiIbaraki<Graph, CapacityMap,
167
                                SetUnitCapacityTraits> {
168
      typedef NagamochiIbaraki<Graph, CapacityMap,
169
                               SetUnitCapacityTraits> Create;
170
    };
171

	
172

	
173
    template <class H, class CR>
174
    struct SetHeapTraits : public Traits {
175
      typedef CR HeapCrossRef;
176
      typedef H Heap;
177
      static HeapCrossRef *createHeapCrossRef(int num) {
178
        LEMON_ASSERT(false, "HeapCrossRef is not initialized");
179
        return 0; // ignore warnings
180
      }
181
      static Heap *createHeap(HeapCrossRef &) {
182
        LEMON_ASSERT(false, "Heap is not initialized");
183
        return 0; // ignore warnings
184
      }
185
    };
186

	
187
    /// \brief \ref named-templ-param "Named parameter" for setting
188
    /// heap and cross reference type
189
    ///
190
    /// \ref named-templ-param "Named parameter" for setting heap and
191
    /// cross reference type. The heap has to maximize the priorities.
192
    template <class H, class CR = RangeMap<int> >
193
    struct SetHeap
194
      : public NagamochiIbaraki<Graph, CapacityMap, SetHeapTraits<H, CR> > {
195
      typedef NagamochiIbaraki< Graph, CapacityMap, SetHeapTraits<H, CR> >
196
      Create;
197
    };
198

	
199
    template <class H, class CR>
200
    struct SetStandardHeapTraits : public Traits {
201
      typedef CR HeapCrossRef;
202
      typedef H Heap;
203
      static HeapCrossRef *createHeapCrossRef(int size) {
204
        return new HeapCrossRef(size);
205
      }
206
      static Heap *createHeap(HeapCrossRef &crossref) {
207
        return new Heap(crossref);
208
      }
209
    };
210

	
211
    /// \brief \ref named-templ-param "Named parameter" for setting
212
    /// heap and cross reference type with automatic allocation
213
    ///
214
    /// \ref named-templ-param "Named parameter" for setting heap and
215
    /// cross reference type with automatic allocation. They should
216
    /// have standard constructor interfaces to be able to
217
    /// automatically created by the algorithm (i.e. the graph should
218
    /// be passed to the constructor of the cross reference and the
219
    /// cross reference should be passed to the constructor of the
220
    /// heap). However, external heap and cross reference objects
221
    /// could also be passed to the algorithm using the \ref heap()
222
    /// function before calling \ref run() or \ref init(). The heap
223
    /// has to maximize the priorities.
224
    /// \sa SetHeap
225
    template <class H, class CR = RangeMap<int> >
226
    struct SetStandardHeap
227
      : public NagamochiIbaraki<Graph, CapacityMap,
228
                                SetStandardHeapTraits<H, CR> > {
229
      typedef NagamochiIbaraki<Graph, CapacityMap,
230
                               SetStandardHeapTraits<H, CR> > Create;
231
    };
232

	
233
    ///@}
234

	
235

	
236
  private:
237

	
238
    const Graph &_graph;
239
    const CapacityMap *_capacity;
240
    bool _local_capacity; // unit capacity
241

	
242
    struct ArcData {
243
      typename Graph::Node target;
244
      int prev, next;
245
    };
246
    struct EdgeData {
247
      Value capacity;
248
      Value cut;
249
    };
250

	
251
    struct NodeData {
252
      int first_arc;
253
      typename Graph::Node prev, next;
254
      int curr_arc;
255
      typename Graph::Node last_rep;
256
      Value sum;
257
    };
258

	
259
    typename Graph::template NodeMap<NodeData> *_nodes;
260
    std::vector<ArcData> _arcs;
261
    std::vector<EdgeData> _edges;
262

	
263
    typename Graph::Node _first_node;
264
    int _node_num;
265

	
266
    Value _min_cut;
267

	
268
    HeapCrossRef *_heap_cross_ref;
269
    bool _local_heap_cross_ref;
270
    Heap *_heap;
271
    bool _local_heap;
272

	
273
    typedef typename Graph::template NodeMap<typename Graph::Node> NodeList;
274
    NodeList *_next_rep;
275

	
276
    typedef typename Graph::template NodeMap<bool> MinCutMap;
277
    MinCutMap *_cut_map;
278

	
279
    void createStructures() {
280
      if (!_nodes) {
281
        _nodes = new (typename Graph::template NodeMap<NodeData>)(_graph);
282
      }
283
      if (!_capacity) {
284
        _local_capacity = true;
285
        _capacity = Traits::createCapacityMap(_graph);
286
      }
287
      if (!_heap_cross_ref) {
288
        _local_heap_cross_ref = true;
289
        _heap_cross_ref = Traits::createHeapCrossRef(_graph);
290
      }
291
      if (!_heap) {
292
        _local_heap = true;
293
        _heap = Traits::createHeap(*_heap_cross_ref);
294
      }
295
      if (!_next_rep) {
296
        _next_rep = new NodeList(_graph);
297
      }
298
      if (!_cut_map) {
299
        _cut_map = new MinCutMap(_graph);
300
      }
301
    }
302

	
303
  public :
304

	
305
    typedef NagamochiIbaraki Create;
306

	
307

	
308
    /// \brief Constructor.
309
    ///
310
    /// \param graph The graph the algorithm runs on.
311
    /// \param capacity The capacity map used by the algorithm.
312
    NagamochiIbaraki(const Graph& graph, const CapacityMap& capacity)
313
      : _graph(graph), _capacity(&capacity), _local_capacity(false),
314
        _nodes(0), _arcs(), _edges(), _min_cut(),
315
        _heap_cross_ref(0), _local_heap_cross_ref(false),
316
        _heap(0), _local_heap(false),
317
        _next_rep(0), _cut_map(0) {}
318

	
319
    /// \brief Constructor.
320
    ///
321
    /// This constructor can be used only when the Traits class
322
    /// defines how can the local capacity map be instantiated.
323
    /// If the SetUnitCapacity used the algorithm automatically
324
    /// constructs the capacity map.
325
    ///
326
    ///\param graph The graph the algorithm runs on.
327
    NagamochiIbaraki(const Graph& graph)
328
      : _graph(graph), _capacity(0), _local_capacity(false),
329
        _nodes(0), _arcs(), _edges(), _min_cut(),
330
        _heap_cross_ref(0), _local_heap_cross_ref(false),
331
        _heap(0), _local_heap(false),
332
        _next_rep(0), _cut_map(0) {}
333

	
334
    /// \brief Destructor.
335
    ///
336
    /// Destructor.
337
    ~NagamochiIbaraki() {
338
      if (_local_capacity) delete _capacity;
339
      if (_nodes) delete _nodes;
340
      if (_local_heap) delete _heap;
341
      if (_local_heap_cross_ref) delete _heap_cross_ref;
342
      if (_next_rep) delete _next_rep;
343
      if (_cut_map) delete _cut_map;
344
    }
345

	
346
    /// \brief Sets the heap and the cross reference used by algorithm.
347
    ///
348
    /// Sets the heap and the cross reference used by algorithm.
349
    /// If you don't use this function before calling \ref run(),
350
    /// it will allocate one. The destuctor deallocates this
351
    /// automatically allocated heap and cross reference, of course.
352
    /// \return <tt> (*this) </tt>
353
    NagamochiIbaraki &heap(Heap& hp, HeapCrossRef &cr)
354
    {
355
      if (_local_heap_cross_ref) {
356
        delete _heap_cross_ref;
357
        _local_heap_cross_ref = false;
358
      }
359
      _heap_cross_ref = &cr;
360
      if (_local_heap) {
361
        delete _heap;
362
        _local_heap = false;
363
      }
364
      _heap = &hp;
365
      return *this;
366
    }
367

	
368
    /// \name Execution control
369
    /// The simplest way to execute the algorithm is to use
370
    /// one of the member functions called \c run().
371
    /// \n
372
    /// If you need more control on the execution,
373
    /// first you must call \ref init() and then call the start()
374
    /// or proper times the processNextPhase() member functions.
375

	
376
    ///@{
377

	
378
    /// \brief Initializes the internal data structures.
379
    ///
380
    /// Initializes the internal data structures.
381
    void init() {
382
      createStructures();
383

	
384
      int edge_num = countEdges(_graph);
385
      _edges.resize(edge_num);
386
      _arcs.resize(2 * edge_num);
387

	
388
      typename Graph::Node prev = INVALID;
389
      _node_num = 0;
390
      for (typename Graph::NodeIt n(_graph); n != INVALID; ++n) {
391
        (*_cut_map)[n] = false;
392
        (*_next_rep)[n] = INVALID;
393
        (*_nodes)[n].last_rep = n;
394
        (*_nodes)[n].first_arc = -1;
395
        (*_nodes)[n].curr_arc = -1;
396
        (*_nodes)[n].prev = prev;
397
        if (prev != INVALID) {
398
          (*_nodes)[prev].next = n;
399
        }
400
        (*_nodes)[n].next = INVALID;
401
        (*_nodes)[n].sum = 0;
402
        prev = n;
403
        ++_node_num;
404
      }
405

	
406
      _first_node = typename Graph::NodeIt(_graph);
407

	
408
      int index = 0;
409
      for (typename Graph::NodeIt n(_graph); n != INVALID; ++n) {
410
        for (typename Graph::OutArcIt a(_graph, n); a != INVALID; ++a) {
411
          typename Graph::Node m = _graph.target(a);
412
          
413
          if (!(n < m)) continue;
414

	
415
          (*_nodes)[n].sum += (*_capacity)[a];
416
          (*_nodes)[m].sum += (*_capacity)[a];
417
          
418
          int c = (*_nodes)[m].curr_arc;
419
          if (c != -1 && _arcs[c ^ 1].target == n) {
420
            _edges[c >> 1].capacity += (*_capacity)[a];
421
          } else {
422
            _edges[index].capacity = (*_capacity)[a];
423
            
424
            _arcs[index << 1].prev = -1;
425
            if ((*_nodes)[n].first_arc != -1) {
426
              _arcs[(*_nodes)[n].first_arc].prev = (index << 1);
427
            }
428
            _arcs[index << 1].next = (*_nodes)[n].first_arc;
429
            (*_nodes)[n].first_arc = (index << 1);
430
            _arcs[index << 1].target = m;
431

	
432
            (*_nodes)[m].curr_arc = (index << 1);
433
            
434
            _arcs[(index << 1) | 1].prev = -1;
435
            if ((*_nodes)[m].first_arc != -1) {
436
              _arcs[(*_nodes)[m].first_arc].prev = ((index << 1) | 1);
437
            }
438
            _arcs[(index << 1) | 1].next = (*_nodes)[m].first_arc;
439
            (*_nodes)[m].first_arc = ((index << 1) | 1);
440
            _arcs[(index << 1) | 1].target = n;
441
            
442
            ++index;
443
          }
444
        }
445
      }
446

	
447
      typename Graph::Node cut_node = INVALID;
448
      _min_cut = std::numeric_limits<Value>::max();
449

	
450
      for (typename Graph::Node n = _first_node; 
451
           n != INVALID; n = (*_nodes)[n].next) {
452
        if ((*_nodes)[n].sum < _min_cut) {
453
          cut_node = n;
454
          _min_cut = (*_nodes)[n].sum;
455
        }
456
      }
457
      (*_cut_map)[cut_node] = true;
458
      if (_min_cut == 0) {
459
        _first_node = INVALID;
460
      }
461
    }
462

	
463
  public:
464

	
465
    /// \brief Processes the next phase
466
    ///
467
    /// Processes the next phase in the algorithm. It must be called
468
    /// at most one less the number of the nodes in the graph.
469
    ///
470
    ///\return %True when the algorithm finished.
471
    bool processNextPhase() {
472
      if (_first_node == INVALID) return true;
473

	
474
      _heap->clear();
475
      for (typename Graph::Node n = _first_node; 
476
           n != INVALID; n = (*_nodes)[n].next) {
477
        (*_heap_cross_ref)[n] = Heap::PRE_HEAP;
478
      }
479

	
480
      std::vector<typename Graph::Node> order;
481
      order.reserve(_node_num);
482
      int sep = 0;
483

	
484
      Value alpha = 0;
485
      Value pmc = std::numeric_limits<Value>::max();
486

	
487
      _heap->push(_first_node, static_cast<Value>(0));
488
      while (!_heap->empty()) {
489
        typename Graph::Node n = _heap->top();
490
        Value v = _heap->prio();
491

	
492
        _heap->pop();
493
        for (int a = (*_nodes)[n].first_arc; a != -1; a = _arcs[a].next) {
494
          switch (_heap->state(_arcs[a].target)) {
495
          case Heap::PRE_HEAP: 
496
            {
497
              Value nv = _edges[a >> 1].capacity;
498
              _heap->push(_arcs[a].target, nv);
499
              _edges[a >> 1].cut = nv;
500
            } break;
501
          case Heap::IN_HEAP:
502
            {
503
              Value nv = _edges[a >> 1].capacity + (*_heap)[_arcs[a].target];
504
              _heap->decrease(_arcs[a].target, nv);
505
              _edges[a >> 1].cut = nv;
506
            } break;
507
          case Heap::POST_HEAP:
508
            break;
509
          }
510
        }
511

	
512
        alpha += (*_nodes)[n].sum;
513
        alpha -= 2 * v;
514

	
515
        order.push_back(n);
516
        if (!_heap->empty()) {
517
          if (alpha < pmc) {
518
            pmc = alpha;
519
            sep = order.size();
520
          }
521
        }
522
      }
523

	
524
      if (static_cast<int>(order.size()) < _node_num) {
525
        _first_node = INVALID;
526
        for (typename Graph::NodeIt n(_graph); n != INVALID; ++n) {
527
          (*_cut_map)[n] = false;
528
        }
529
        for (int i = 0; i < static_cast<int>(order.size()); ++i) {
530
          typename Graph::Node n = order[i];
531
          while (n != INVALID) {
532
            (*_cut_map)[n] = true;
533
            n = (*_next_rep)[n];
534
          }
535
        }
536
        _min_cut = 0;
537
        return true;
538
      }
539

	
540
      if (pmc < _min_cut) {
541
        for (typename Graph::NodeIt n(_graph); n != INVALID; ++n) {
542
          (*_cut_map)[n] = false;
543
        }
544
        for (int i = 0; i < sep; ++i) {
545
          typename Graph::Node n = order[i];
546
          while (n != INVALID) {
547
            (*_cut_map)[n] = true;
548
            n = (*_next_rep)[n];
549
          }
550
        }
551
        _min_cut = pmc;
552
      }
553

	
554
      for (typename Graph::Node n = _first_node;
555
           n != INVALID; n = (*_nodes)[n].next) {
556
        bool merged = false;
557
        for (int a = (*_nodes)[n].first_arc; a != -1; a = _arcs[a].next) {
558
          if (!(_edges[a >> 1].cut < pmc)) {
559
            if (!merged) {
560
              for (int b = (*_nodes)[n].first_arc; b != -1; b = _arcs[b].next) {
561
                (*_nodes)[_arcs[b].target].curr_arc = b;          
562
              }
563
              merged = true;
564
            }
565
            typename Graph::Node m = _arcs[a].target;
566
            int nb = 0;
567
            for (int b = (*_nodes)[m].first_arc; b != -1; b = nb) {
568
              nb = _arcs[b].next;
569
              if ((b ^ a) == 1) continue;
570
              typename Graph::Node o = _arcs[b].target;
571
              int c = (*_nodes)[o].curr_arc; 
572
              if (c != -1 && _arcs[c ^ 1].target == n) {
573
                _edges[c >> 1].capacity += _edges[b >> 1].capacity;
574
                (*_nodes)[n].sum += _edges[b >> 1].capacity;
575
                if (_edges[b >> 1].cut < _edges[c >> 1].cut) {
576
                  _edges[b >> 1].cut = _edges[c >> 1].cut;
577
                }
578
                if (_arcs[b ^ 1].prev != -1) {
579
                  _arcs[_arcs[b ^ 1].prev].next = _arcs[b ^ 1].next;
580
                } else {
581
                  (*_nodes)[o].first_arc = _arcs[b ^ 1].next;
582
                }
583
                if (_arcs[b ^ 1].next != -1) {
584
                  _arcs[_arcs[b ^ 1].next].prev = _arcs[b ^ 1].prev;
585
                }
586
              } else {
587
                if (_arcs[a].next != -1) {
588
                  _arcs[_arcs[a].next].prev = b;
589
                }
590
                _arcs[b].next = _arcs[a].next;
591
                _arcs[b].prev = a;
592
                _arcs[a].next = b;
593
                _arcs[b ^ 1].target = n;
594

	
595
                (*_nodes)[n].sum += _edges[b >> 1].capacity;
596
                (*_nodes)[o].curr_arc = b;
597
              }
598
            }
599

	
600
            if (_arcs[a].prev != -1) {
601
              _arcs[_arcs[a].prev].next = _arcs[a].next;
602
            } else {
603
              (*_nodes)[n].first_arc = _arcs[a].next;
604
            }            
605
            if (_arcs[a].next != -1) {
606
              _arcs[_arcs[a].next].prev = _arcs[a].prev;
607
            }
608

	
609
            (*_nodes)[n].sum -= _edges[a >> 1].capacity;
610
            (*_next_rep)[(*_nodes)[n].last_rep] = m;
611
            (*_nodes)[n].last_rep = (*_nodes)[m].last_rep;
612
            
613
            if ((*_nodes)[m].prev != INVALID) {
614
              (*_nodes)[(*_nodes)[m].prev].next = (*_nodes)[m].next;
615
            } else{
616
              _first_node = (*_nodes)[m].next;
617
            }
618
            if ((*_nodes)[m].next != INVALID) {
619
              (*_nodes)[(*_nodes)[m].next].prev = (*_nodes)[m].prev;
620
            }
621
            --_node_num;
622
          }
623
        }
624
      }
625

	
626
      if (_node_num == 1) {
627
        _first_node = INVALID;
628
        return true;
629
      }
630

	
631
      return false;
632
    }
633

	
634
    /// \brief Executes the algorithm.
635
    ///
636
    /// Executes the algorithm.
637
    ///
638
    /// \pre init() must be called
639
    void start() {
640
      while (!processNextPhase()) {}
641
    }
642

	
643

	
644
    /// \brief Runs %NagamochiIbaraki algorithm.
645
    ///
646
    /// This method runs the %Min cut algorithm
647
    ///
648
    /// \note mc.run(s) is just a shortcut of the following code.
649
    ///\code
650
    ///  mc.init();
651
    ///  mc.start();
652
    ///\endcode
653
    void run() {
654
      init();
655
      start();
656
    }
657

	
658
    ///@}
659

	
660
    /// \name Query Functions
661
    ///
662
    /// The result of the %NagamochiIbaraki
663
    /// algorithm can be obtained using these functions.\n
664
    /// Before the use of these functions, either run() or start()
665
    /// must be called.
666

	
667
    ///@{
668

	
669
    /// \brief Returns the min cut value.
670
    ///
671
    /// Returns the min cut value if the algorithm finished.
672
    /// After the first processNextPhase() it is a value of a
673
    /// valid cut in the graph.
674
    Value minCutValue() const {
675
      return _min_cut;
676
    }
677

	
678
    /// \brief Returns a min cut in a NodeMap.
679
    ///
680
    /// It sets the nodes of one of the two partitions to true and
681
    /// the other partition to false.
682
    /// \param cutMap A \ref concepts::WriteMap "writable" node map with
683
    /// \c bool (or convertible) value type.
684
    template <typename CutMap>
685
    Value minCutMap(CutMap& cutMap) const {
686
      for (typename Graph::NodeIt n(_graph); n != INVALID; ++n) {
687
        cutMap.set(n, (*_cut_map)[n]);
688
      }
689
      return minCutValue();
690
    }
691

	
692
    ///@}
693

	
694
  };
695
}
696

	
697
#endif
Show white space 128 line context
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-2010
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
#include <sstream>
20

	
21
#include <lemon/smart_graph.h>
22
#include <lemon/adaptors.h>
23
#include <lemon/concepts/graph.h>
24
#include <lemon/concepts/maps.h>
25
#include <lemon/lgf_reader.h>
26
#include <lemon/nagamochi_ibaraki.h>
27

	
28
#include "test_tools.h"
29

	
30
using namespace lemon;
31
using namespace std;
32

	
33
const std::string lgf =
34
  "@nodes\n"
35
  "label\n"
36
  "0\n"
37
  "1\n"
38
  "2\n"
39
  "3\n"
40
  "4\n"
41
  "5\n"
42
  "@edges\n"
43
  "     cap1 cap2 cap3\n"
44
  "0 1  1    1    1   \n"
45
  "0 2  2    2    4   \n"
46
  "1 2  4    4    4   \n"
47
  "3 4  1    1    1   \n"
48
  "3 5  2    2    4   \n"
49
  "4 5  4    4    4   \n"
50
  "2 3  1    6    6   \n";
51

	
52
void checkNagamochiIbarakiCompile()
53
{
54
  typedef int Value;
55
  typedef concepts::Graph Graph;
56

	
57
  typedef Graph::Node Node;
58
  typedef Graph::Edge Edge;
59
  typedef concepts::ReadMap<Edge, Value> CapMap;
60
  typedef concepts::WriteMap<Node, bool> CutMap;
61

	
62
  Graph g;
63
  Node n;
64
  CapMap cap;
65
  CutMap cut;
66
  Value v;
67
  bool b;
68

	
69
  NagamochiIbaraki<Graph, CapMap> ni_test(g, cap);
70
  const NagamochiIbaraki<Graph, CapMap>& const_ni_test = ni_test;
71

	
72
  ni_test.init();
73
  ni_test.start();
74
  b = ni_test.processNextPhase();
75
  ni_test.run();
76

	
77
  v = const_ni_test.minCutValue();
78
  v = const_ni_test.minCutMap(cut);
79
}
80

	
81
template <typename Graph, typename CapMap, typename CutMap>
82
typename CapMap::Value
83
  cutValue(const Graph& graph, const CapMap& cap, const CutMap& cut)
84
{
85
  typename CapMap::Value sum = 0;
86
  for (typename Graph::EdgeIt e(graph); e != INVALID; ++e) {
87
    if (cut[graph.u(e)] != cut[graph.v(e)]) {
88
      sum += cap[e];
89
    }
90
  }
91
  return sum;
92
}
93

	
94
int main() {
95
  SmartGraph graph;
96
  SmartGraph::EdgeMap<int> cap1(graph), cap2(graph), cap3(graph);
97
  SmartGraph::NodeMap<bool> cut(graph);
98

	
99
  istringstream input(lgf);
100
  graphReader(graph, input)
101
    .edgeMap("cap1", cap1)
102
    .edgeMap("cap2", cap2)
103
    .edgeMap("cap3", cap3)
104
    .run();
105

	
106
  {
107
    NagamochiIbaraki<SmartGraph> ni(graph, cap1);
108
    ni.run();
109
    ni.minCutMap(cut);
110

	
111
    check(ni.minCutValue() == 1, "Wrong cut value");
112
    check(ni.minCutValue() == cutValue(graph, cap1, cut), "Wrong cut value");
113
  }
114
  {
115
    NagamochiIbaraki<SmartGraph> ni(graph, cap2);
116
    ni.run();
117
    ni.minCutMap(cut);
118

	
119
    check(ni.minCutValue() == 3, "Wrong cut value");
120
    check(ni.minCutValue() == cutValue(graph, cap2, cut), "Wrong cut value");
121
  }
122
  {
123
    NagamochiIbaraki<SmartGraph> ni(graph, cap3);
124
    ni.run();
125
    ni.minCutMap(cut);
126

	
127
    check(ni.minCutValue() == 5, "Wrong cut value");
128
    check(ni.minCutValue() == cutValue(graph, cap3, cut), "Wrong cut value");
129
  }
130
  {
131
    NagamochiIbaraki<SmartGraph>::SetUnitCapacity::Create ni(graph);
132
    ni.run();
133
    ni.minCutMap(cut);
134

	
135
    ConstMap<SmartGraph::Edge, int> cap4(1);
136
    check(ni.minCutValue() == 1, "Wrong cut value");
137
    check(ni.minCutValue() == cutValue(graph, cap4, cut), "Wrong cut value");
138
  }
139

	
140
  return 0;
141
}
Show white space 128 line context
1 1
CMAKE_MINIMUM_REQUIRED(VERSION 2.6)
2 2

	
3 3
SET(PROJECT_NAME "LEMON")
4 4
PROJECT(${PROJECT_NAME})
5 5

	
6 6
INCLUDE(FindPythonInterp)
7
INCLUDE(FindWget)
7 8

	
8 9
IF(EXISTS ${PROJECT_SOURCE_DIR}/cmake/version.cmake)
9 10
  INCLUDE(${PROJECT_SOURCE_DIR}/cmake/version.cmake)
10 11
ELSEIF(DEFINED ENV{LEMON_VERSION})
11 12
  SET(LEMON_VERSION $ENV{LEMON_VERSION} CACHE STRING "LEMON version string.")
12 13
ELSE()
13 14
  EXECUTE_PROCESS(
14 15
    COMMAND ${PYTHON_EXECUTABLE} ./scripts/chg-len.py
15 16
    WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
16 17
    OUTPUT_VARIABLE HG_REVISION_PATH
17 18
    ERROR_QUIET
18 19
    OUTPUT_STRIP_TRAILING_WHITESPACE
19 20
  )
20 21
  EXECUTE_PROCESS(
21 22
    COMMAND hg id -i
22 23
    WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
23 24
    OUTPUT_VARIABLE HG_REVISION
24 25
    ERROR_QUIET
25 26
    OUTPUT_STRIP_TRAILING_WHITESPACE
26 27
  )
27 28
  IF(HG_REVISION STREQUAL "")
28 29
    SET(HG_REVISION_ID "hg-tip")
29 30
  ELSE()
30 31
    IF(HG_REVISION_PATH STREQUAL "")
31 32
      SET(HG_REVISION_ID ${HG_REVISION})
32 33
    ELSE()
33 34
      SET(HG_REVISION_ID ${HG_REVISION_PATH}.${HG_REVISION})
34 35
    ENDIF()
35 36
  ENDIF()
36 37
  SET(LEMON_VERSION ${HG_REVISION_ID} CACHE STRING "LEMON version string.")
37 38
ENDIF()
38 39

	
39 40
SET(PROJECT_VERSION ${LEMON_VERSION})
40 41

	
41 42
SET(CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR}/cmake)
42 43

	
43 44
FIND_PACKAGE(Doxygen)
44 45
FIND_PACKAGE(Ghostscript)
45 46
FIND_PACKAGE(GLPK 4.33)
46 47
FIND_PACKAGE(CPLEX)
47 48
FIND_PACKAGE(COIN)
48 49

	
49 50
IF(DEFINED ENV{LEMON_CXX_WARNING})
50 51
  SET(CXX_WARNING $ENV{LEMON_CXX_WARNING})
51 52
ELSE()
52 53
  IF(CMAKE_COMPILER_IS_GNUCXX)
53 54
    SET(CXX_WARNING "-Wall -W -Wunused -Wformat=2 -Wctor-dtor-privacy -Wnon-virtual-dtor -Wno-char-subscripts -Wwrite-strings -Wno-char-subscripts -Wreturn-type -Wcast-qual -Wcast-align -Wsign-promo -Woverloaded-virtual -ansi -fno-strict-aliasing -Wold-style-cast -Wno-unknown-pragmas")
54 55
    SET(CMAKE_CXX_FLAGS_DEBUG CACHE STRING "-ggdb")
55 56
    SET(CMAKE_C_FLAGS_DEBUG CACHE STRING "-ggdb")
56 57
  ELSEIF(MSVC)
57 58
    # This part is unnecessary 'casue the same is set by the lemon/core.h.
58 59
    # Still keep it as an example.
59 60
    SET(CXX_WARNING "/wd4250 /wd4355 /wd4503 /wd4800 /wd4996")
60 61
    # Suppressed warnings:
61 62
    # C4250: 'class1' : inherits 'class2::member' via dominance
62 63
    # C4355: 'this' : used in base member initializer list
63 64
    # C4503: 'function' : decorated name length exceeded, name was truncated
64 65
    # C4800: 'type' : forcing value to bool 'true' or 'false'
65 66
    #        (performance warning)
66 67
    # C4996: 'function': was declared deprecated
67 68
  ELSE()
68 69
    SET(CXX_WARNING "-Wall -W")
69 70
  ENDIF()
70 71
ENDIF()
Show white space 128 line context
1 1
SET(PACKAGE_NAME ${PROJECT_NAME})
2 2
SET(PACKAGE_VERSION ${PROJECT_VERSION})
3 3
SET(abs_top_srcdir ${PROJECT_SOURCE_DIR})
4 4
SET(abs_top_builddir ${PROJECT_BINARY_DIR})
5 5

	
6
SET(LEMON_DOC_SOURCE_BROWSER "NO" CACHE STRING "Include source into the doc (YES/NO).")
7

	
6 8
CONFIGURE_FILE(
7 9
  ${PROJECT_SOURCE_DIR}/doc/Doxyfile.in
8 10
  ${PROJECT_BINARY_DIR}/doc/Doxyfile
9 11
  @ONLY
10 12
)
11 13

	
12 14
IF(DOXYGEN_EXECUTABLE AND PYTHONINTERP_FOUND AND GHOSTSCRIPT_EXECUTABLE)
13 15
  FILE(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/html/)
14 16
  SET(GHOSTSCRIPT_OPTIONS -dNOPAUSE -dBATCH -q -dEPSCrop -dTextAlphaBits=4 -dGraphicsAlphaBits=4 -sDEVICE=pngalpha)
15 17
  ADD_CUSTOM_TARGET(html
16 18
    COMMAND ${CMAKE_COMMAND} -E remove_directory gen-images
17 19
    COMMAND ${CMAKE_COMMAND} -E make_directory gen-images
18 20
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/bipartite_matching.png ${CMAKE_CURRENT_SOURCE_DIR}/images/bipartite_matching.eps
19 21
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/bipartite_partitions.png ${CMAKE_CURRENT_SOURCE_DIR}/images/bipartite_partitions.eps
20 22
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/connected_components.png ${CMAKE_CURRENT_SOURCE_DIR}/images/connected_components.eps
21 23
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/edge_biconnected_components.png ${CMAKE_CURRENT_SOURCE_DIR}/images/edge_biconnected_components.eps
22 24
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/grid_graph.png ${CMAKE_CURRENT_SOURCE_DIR}/images/grid_graph.eps
23 25
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/matching.png ${CMAKE_CURRENT_SOURCE_DIR}/images/matching.eps
24 26
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/node_biconnected_components.png ${CMAKE_CURRENT_SOURCE_DIR}/images/node_biconnected_components.eps
25 27
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/nodeshape_0.png ${CMAKE_CURRENT_SOURCE_DIR}/images/nodeshape_0.eps
26 28
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/nodeshape_1.png ${CMAKE_CURRENT_SOURCE_DIR}/images/nodeshape_1.eps
27 29
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/nodeshape_2.png ${CMAKE_CURRENT_SOURCE_DIR}/images/nodeshape_2.eps
28 30
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/nodeshape_3.png ${CMAKE_CURRENT_SOURCE_DIR}/images/nodeshape_3.eps
29 31
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/nodeshape_4.png ${CMAKE_CURRENT_SOURCE_DIR}/images/nodeshape_4.eps
30 32
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/planar.png ${CMAKE_CURRENT_SOURCE_DIR}/images/planar.eps
31 33
    COMMAND ${GHOSTSCRIPT_EXECUTABLE} ${GHOSTSCRIPT_OPTIONS} -r18 -sOutputFile=gen-images/strongly_connected_components.png ${CMAKE_CURRENT_SOURCE_DIR}/images/strongly_connected_components.eps
32 34
    COMMAND ${CMAKE_COMMAND} -E remove_directory html
33 35
    COMMAND ${PYTHON_EXECUTABLE} ${PROJECT_SOURCE_DIR}/scripts/bib2dox.py ${CMAKE_CURRENT_SOURCE_DIR}/references.bib >references.dox
34 36
    COMMAND ${DOXYGEN_EXECUTABLE} Doxyfile
35 37
    WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
36 38
  )
37 39

	
38 40
  SET_TARGET_PROPERTIES(html PROPERTIES PROJECT_LABEL BUILD_DOC)
39 41

	
40 42
  IF(UNIX)
41 43
    INSTALL(
42 44
      DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/html/
43 45
      DESTINATION share/doc/lemon/html
44 46
      COMPONENT html_documentation
45 47
    )
46 48
  ELSEIF(WIN32)
47 49
    INSTALL(
48 50
      DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/html/
49 51
      DESTINATION doc
50 52
      COMPONENT html_documentation
51 53
    )
52 54
  ENDIF()
53 55

	
54 56
ENDIF()
57

	
58
IF(WGET_FOUND)
59
ADD_CUSTOM_TARGET(update-external-tags
60
  COMMAND ${CMAKE_COMMAND} -E make_directory dl
61
  # COMMAND ${CMAKE_COMMAND} -E copy libstdc++.tag dl
62
  COMMAND ${WGET_EXECUTABLE} wget -P dl -N libstdc++.tag.tmp http://gcc.gnu.org/onlinedocs/libstdc++/latest-doxygen/libstdc++.tag
63
  COMMAND ${CMAKE_COMMAND} -E rename dl/libstdc++.tag libstdc++.tag
64
  COMMAND ${CMAKE_COMMAND} -E remove dl/libstdc++.tag
65
  COMMAND ${CMAKE_COMMAND} -E remove_directory dl
66
  WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
67
  )
68
ENDIF()
Show white space 128 line context
... ...
@@ -9,258 +9,258 @@
9 9
OUTPUT_DIRECTORY       = 
10 10
CREATE_SUBDIRS         = NO
11 11
OUTPUT_LANGUAGE        = English
12 12
BRIEF_MEMBER_DESC      = YES
13 13
REPEAT_BRIEF           = NO
14 14
ABBREVIATE_BRIEF       = 
15 15
ALWAYS_DETAILED_SEC    = NO
16 16
INLINE_INHERITED_MEMB  = NO
17 17
FULL_PATH_NAMES        = YES
18 18
STRIP_FROM_PATH        = "@abs_top_srcdir@"
19 19
STRIP_FROM_INC_PATH    = "@abs_top_srcdir@"
20 20
SHORT_NAMES            = YES
21 21
JAVADOC_AUTOBRIEF      = NO
22 22
QT_AUTOBRIEF           = NO
23 23
MULTILINE_CPP_IS_BRIEF = NO
24 24
INHERIT_DOCS           = NO
25 25
SEPARATE_MEMBER_PAGES  = NO
26 26
TAB_SIZE               = 8
27 27
ALIASES                = 
28 28
OPTIMIZE_OUTPUT_FOR_C  = NO
29 29
OPTIMIZE_OUTPUT_JAVA   = NO
30 30
OPTIMIZE_FOR_FORTRAN   = NO
31 31
OPTIMIZE_OUTPUT_VHDL   = NO
32 32
BUILTIN_STL_SUPPORT    = YES
33 33
CPP_CLI_SUPPORT        = NO
34 34
SIP_SUPPORT            = NO
35 35
IDL_PROPERTY_SUPPORT   = YES
36 36
DISTRIBUTE_GROUP_DOC   = NO
37 37
SUBGROUPING            = YES
38 38
TYPEDEF_HIDES_STRUCT   = NO
39 39
SYMBOL_CACHE_SIZE      = 0
40 40
#---------------------------------------------------------------------------
41 41
# Build related configuration options
42 42
#---------------------------------------------------------------------------
43 43
EXTRACT_ALL            = NO
44 44
EXTRACT_PRIVATE        = YES
45 45
EXTRACT_STATIC         = YES
46 46
EXTRACT_LOCAL_CLASSES  = NO
47 47
EXTRACT_LOCAL_METHODS  = NO
48 48
EXTRACT_ANON_NSPACES   = NO
49 49
HIDE_UNDOC_MEMBERS     = YES
50 50
HIDE_UNDOC_CLASSES     = YES
51 51
HIDE_FRIEND_COMPOUNDS  = NO
52 52
HIDE_IN_BODY_DOCS      = NO
53 53
INTERNAL_DOCS          = NO
54 54
CASE_SENSE_NAMES       = YES
55 55
HIDE_SCOPE_NAMES       = YES
56 56
SHOW_INCLUDE_FILES     = YES
57 57
INLINE_INFO            = YES
58 58
SORT_MEMBER_DOCS       = NO
59 59
SORT_BRIEF_DOCS        = NO
60 60
SORT_GROUP_NAMES       = NO
61 61
SORT_BY_SCOPE_NAME     = NO
62 62
GENERATE_TODOLIST      = YES
63 63
GENERATE_TESTLIST      = YES
64 64
GENERATE_BUGLIST       = YES
65 65
GENERATE_DEPRECATEDLIST= YES
66 66
ENABLED_SECTIONS       = 
67 67
MAX_INITIALIZER_LINES  = 5
68 68
SHOW_USED_FILES        = NO
69 69
SHOW_DIRECTORIES       = YES
70 70
SHOW_FILES             = YES
71 71
SHOW_NAMESPACES        = YES
72 72
FILE_VERSION_FILTER    = 
73
LAYOUT_FILE            = DoxygenLayout.xml
73
LAYOUT_FILE            = "@abs_top_srcdir@/doc/DoxygenLayout.xml"
74 74
#---------------------------------------------------------------------------
75 75
# configuration options related to warning and progress messages
76 76
#---------------------------------------------------------------------------
77 77
QUIET                  = NO
78 78
WARNINGS               = YES
79 79
WARN_IF_UNDOCUMENTED   = YES
80 80
WARN_IF_DOC_ERROR      = YES
81 81
WARN_NO_PARAMDOC       = NO
82 82
WARN_FORMAT            = "$file:$line: $text"
83 83
WARN_LOGFILE           = doxygen.log
84 84
#---------------------------------------------------------------------------
85 85
# configuration options related to the input files
86 86
#---------------------------------------------------------------------------
87 87
INPUT                  = "@abs_top_srcdir@/doc" \
88 88
                         "@abs_top_srcdir@/lemon" \
89 89
                         "@abs_top_srcdir@/lemon/bits" \
90 90
                         "@abs_top_srcdir@/lemon/concepts" \
91 91
                         "@abs_top_srcdir@/demo" \
92 92
                         "@abs_top_srcdir@/tools" \
93 93
                         "@abs_top_srcdir@/test/test_tools.h" \
94 94
                         "@abs_top_builddir@/doc/references.dox"
95 95
INPUT_ENCODING         = UTF-8
96 96
FILE_PATTERNS          = *.h \
97 97
                         *.cc \
98 98
                         *.dox
99 99
RECURSIVE              = NO
100 100
EXCLUDE                = 
101 101
EXCLUDE_SYMLINKS       = NO
102 102
EXCLUDE_PATTERNS       = 
103 103
EXCLUDE_SYMBOLS        = 
104 104
EXAMPLE_PATH           = "@abs_top_srcdir@/demo" \
105 105
                         "@abs_top_srcdir@/LICENSE" \
106 106
                         "@abs_top_srcdir@/doc"
107 107
EXAMPLE_PATTERNS       = 
108 108
EXAMPLE_RECURSIVE      = NO
109 109
IMAGE_PATH             = "@abs_top_srcdir@/doc/images" \
110 110
                         "@abs_top_builddir@/doc/gen-images"
111 111
INPUT_FILTER           = 
112 112
FILTER_PATTERNS        = 
113 113
FILTER_SOURCE_FILES    = NO
114 114
#---------------------------------------------------------------------------
115 115
# configuration options related to source browsing
116 116
#---------------------------------------------------------------------------
117
SOURCE_BROWSER         = NO
117
SOURCE_BROWSER         = @LEMON_DOC_SOURCE_BROWSER@
118 118
INLINE_SOURCES         = NO
119 119
STRIP_CODE_COMMENTS    = YES
120 120
REFERENCED_BY_RELATION = NO
121 121
REFERENCES_RELATION    = NO
122 122
REFERENCES_LINK_SOURCE = YES
123 123
USE_HTAGS              = NO
124 124
VERBATIM_HEADERS       = NO
125 125
#---------------------------------------------------------------------------
126 126
# configuration options related to the alphabetical class index
127 127
#---------------------------------------------------------------------------
128 128
ALPHABETICAL_INDEX     = YES
129 129
COLS_IN_ALPHA_INDEX    = 2
130 130
IGNORE_PREFIX          = 
131 131
#---------------------------------------------------------------------------
132 132
# configuration options related to the HTML output
133 133
#---------------------------------------------------------------------------
134 134
GENERATE_HTML          = YES
135 135
HTML_OUTPUT            = html
136 136
HTML_FILE_EXTENSION    = .html
137 137
HTML_HEADER            = 
138 138
HTML_FOOTER            = 
139 139
HTML_STYLESHEET        = 
140 140
HTML_ALIGN_MEMBERS     = YES
141 141
HTML_DYNAMIC_SECTIONS  = NO
142 142
GENERATE_DOCSET        = NO
143 143
DOCSET_FEEDNAME        = "Doxygen generated docs"
144 144
DOCSET_BUNDLE_ID       = org.doxygen.Project
145 145
GENERATE_HTMLHELP      = NO
146 146
CHM_FILE               = 
147 147
HHC_LOCATION           = 
148 148
GENERATE_CHI           = NO
149 149
CHM_INDEX_ENCODING     = 
150 150
BINARY_TOC             = NO
151 151
TOC_EXPAND             = NO
152 152
GENERATE_QHP           = NO
153 153
QCH_FILE               = 
154 154
QHP_NAMESPACE          = org.doxygen.Project
155 155
QHP_VIRTUAL_FOLDER     = doc
156 156
QHG_LOCATION           = 
157 157
DISABLE_INDEX          = NO
158 158
ENUM_VALUES_PER_LINE   = 4
159 159
GENERATE_TREEVIEW      = NO
160 160
TREEVIEW_WIDTH         = 250
161 161
FORMULA_FONTSIZE       = 10
162 162
#---------------------------------------------------------------------------
163 163
# configuration options related to the LaTeX output
164 164
#---------------------------------------------------------------------------
165 165
GENERATE_LATEX         = NO
166 166
LATEX_OUTPUT           = latex
167 167
LATEX_CMD_NAME         = latex
168 168
MAKEINDEX_CMD_NAME     = makeindex
169 169
COMPACT_LATEX          = YES
170 170
PAPER_TYPE             = a4wide
171 171
EXTRA_PACKAGES         = amsmath \
172 172
                         amssymb
173 173
LATEX_HEADER           = 
174 174
PDF_HYPERLINKS         = YES
175 175
USE_PDFLATEX           = YES
176 176
LATEX_BATCHMODE        = NO
177 177
LATEX_HIDE_INDICES     = NO
178 178
#---------------------------------------------------------------------------
179 179
# configuration options related to the RTF output
180 180
#---------------------------------------------------------------------------
181 181
GENERATE_RTF           = NO
182 182
RTF_OUTPUT             = rtf
183 183
COMPACT_RTF            = NO
184 184
RTF_HYPERLINKS         = NO
185 185
RTF_STYLESHEET_FILE    = 
186 186
RTF_EXTENSIONS_FILE    = 
187 187
#---------------------------------------------------------------------------
188 188
# configuration options related to the man page output
189 189
#---------------------------------------------------------------------------
190 190
GENERATE_MAN           = NO
191 191
MAN_OUTPUT             = man
192 192
MAN_EXTENSION          = .3
193 193
MAN_LINKS              = NO
194 194
#---------------------------------------------------------------------------
195 195
# configuration options related to the XML output
196 196
#---------------------------------------------------------------------------
197 197
GENERATE_XML           = NO
198 198
XML_OUTPUT             = xml
199 199
XML_SCHEMA             = 
200 200
XML_DTD                = 
201 201
XML_PROGRAMLISTING     = YES
202 202
#---------------------------------------------------------------------------
203 203
# configuration options for the AutoGen Definitions output
204 204
#---------------------------------------------------------------------------
205 205
GENERATE_AUTOGEN_DEF   = NO
206 206
#---------------------------------------------------------------------------
207 207
# configuration options related to the Perl module output
208 208
#---------------------------------------------------------------------------
209 209
GENERATE_PERLMOD       = NO
210 210
PERLMOD_LATEX          = NO
211 211
PERLMOD_PRETTY         = YES
212 212
PERLMOD_MAKEVAR_PREFIX = 
213 213
#---------------------------------------------------------------------------
214 214
# Configuration options related to the preprocessor   
215 215
#---------------------------------------------------------------------------
216 216
ENABLE_PREPROCESSING   = YES
217 217
MACRO_EXPANSION        = NO
218 218
EXPAND_ONLY_PREDEF     = NO
219 219
SEARCH_INCLUDES        = YES
220 220
INCLUDE_PATH           = 
221 221
INCLUDE_FILE_PATTERNS  = 
222 222
PREDEFINED             = DOXYGEN
223 223
EXPAND_AS_DEFINED      = 
224 224
SKIP_FUNCTION_MACROS   = YES
225 225
#---------------------------------------------------------------------------
226 226
# Options related to the search engine   
227 227
#---------------------------------------------------------------------------
228
TAGFILES               = "@abs_top_srcdir@/doc/libstdc++.tag = http://gcc.gnu.org/onlinedocs/libstdc++/latest-doxygen/  "
228
TAGFILES               = "@abs_top_builddir@/doc/libstdc++.tag = http://gcc.gnu.org/onlinedocs/libstdc++/latest-doxygen/  "
229 229
GENERATE_TAGFILE       = html/lemon.tag
230 230
ALLEXTERNALS           = NO
231 231
EXTERNAL_GROUPS        = NO
232 232
PERL_PATH              = /usr/bin/perl
233 233
#---------------------------------------------------------------------------
234 234
# Configuration options related to the dot tool   
235 235
#---------------------------------------------------------------------------
236 236
CLASS_DIAGRAMS         = YES
237 237
MSCGEN_PATH            = 
238 238
HIDE_UNDOC_RELATIONS   = YES
239 239
HAVE_DOT               = YES
240 240
DOT_FONTNAME           = FreeSans
241 241
DOT_FONTSIZE           = 10
242 242
DOT_FONTPATH           = 
243 243
CLASS_GRAPH            = YES
244 244
COLLABORATION_GRAPH    = NO
245 245
GROUP_GRAPHS           = NO
246 246
UML_LOOK               = NO
247 247
TEMPLATE_RELATIONS     = NO
248 248
INCLUDE_GRAPH          = NO
249 249
INCLUDED_BY_GRAPH      = NO
250 250
CALL_GRAPH             = NO
251 251
CALLER_GRAPH           = NO
252 252
GRAPHICAL_HIERARCHY    = NO
253 253
DIRECTORY_GRAPH        = NO
254 254
DOT_IMAGE_FORMAT       = png
255 255
DOT_PATH               = 
256 256
DOTFILE_DIRS           = 
257 257
DOT_GRAPH_MAX_NODES    = 50
258 258
MAX_DOT_GRAPH_DEPTH    = 0
259 259
DOT_TRANSPARENT        = NO
260 260
DOT_MULTI_TARGETS      = NO
261 261
GENERATE_LEGEND        = YES
262 262
DOT_CLEANUP            = YES
263 263
#---------------------------------------------------------------------------
264 264
# Configuration::additions related to the search engine   
265 265
#---------------------------------------------------------------------------
266 266
SEARCHENGINE           = NO
Show white space 128 line context
1 1
INCLUDE_DIRECTORIES(
2 2
  ${PROJECT_SOURCE_DIR}
3 3
  ${PROJECT_BINARY_DIR}
4 4
)
5 5

	
6 6
CONFIGURE_FILE(
7 7
  ${CMAKE_CURRENT_SOURCE_DIR}/config.h.cmake
8 8
  ${CMAKE_CURRENT_BINARY_DIR}/config.h
9 9
)
10 10

	
11
CONFIGURE_FILE(
12
  ${CMAKE_CURRENT_SOURCE_DIR}/lemon.pc.cmake
13
  ${CMAKE_CURRENT_BINARY_DIR}/lemon.pc
14
  @ONLY
15
)
16

	
11 17
SET(LEMON_SOURCES
12 18
  arg_parser.cc
13 19
  base.cc
14 20
  color.cc
15 21
  lp_base.cc
16 22
  lp_skeleton.cc
17 23
  random.cc
18 24
  bits/windows.cc
19 25
)
20 26

	
21 27
IF(LEMON_HAVE_GLPK)
22 28
  SET(LEMON_SOURCES ${LEMON_SOURCES} glpk.cc)
23 29
  INCLUDE_DIRECTORIES(${GLPK_INCLUDE_DIRS})
24 30
  IF(WIN32)
25 31
    INSTALL(FILES ${GLPK_BIN_DIR}/glpk.dll DESTINATION bin)
26 32
    INSTALL(FILES ${GLPK_BIN_DIR}/libltdl3.dll DESTINATION bin)
27 33
    INSTALL(FILES ${GLPK_BIN_DIR}/zlib1.dll DESTINATION bin)
28 34
  ENDIF()
29 35
ENDIF()
30 36

	
31 37
IF(LEMON_HAVE_CPLEX)
32 38
  SET(LEMON_SOURCES ${LEMON_SOURCES} cplex.cc)
33 39
  INCLUDE_DIRECTORIES(${CPLEX_INCLUDE_DIRS})
34 40
ENDIF()
35 41

	
36 42
IF(LEMON_HAVE_CLP)
37 43
  SET(LEMON_SOURCES ${LEMON_SOURCES} clp.cc)
38 44
  INCLUDE_DIRECTORIES(${COIN_INCLUDE_DIRS})
39 45
ENDIF()
40 46

	
41 47
IF(LEMON_HAVE_CBC)
42 48
  SET(LEMON_SOURCES ${LEMON_SOURCES} cbc.cc)
43 49
  INCLUDE_DIRECTORIES(${COIN_INCLUDE_DIRS})
44 50
ENDIF()
45 51

	
46 52
ADD_LIBRARY(lemon ${LEMON_SOURCES})
47 53
IF(UNIX)
48 54
  SET_TARGET_PROPERTIES(lemon PROPERTIES OUTPUT_NAME emon)
49 55
ENDIF()
50 56

	
51 57
INSTALL(
52 58
  TARGETS lemon
53 59
  ARCHIVE DESTINATION lib
54 60
  COMPONENT library
55 61
)
56 62

	
57 63
INSTALL(
58 64
  DIRECTORY . bits concepts
59 65
  DESTINATION include/lemon
60 66
  COMPONENT headers
61 67
  FILES_MATCHING PATTERN "*.h"
62 68
)
63 69

	
64 70
INSTALL(
65 71
  FILES ${CMAKE_CURRENT_BINARY_DIR}/config.h
66 72
  DESTINATION include/lemon
67 73
  COMPONENT headers
68 74
)
75

	
76
INSTALL(
77
  FILES ${CMAKE_CURRENT_BINARY_DIR}/lemon.pc
78
  DESTINATION lib/pkgconfig
79
)
80

	
Show white space 128 line context
... ...
@@ -47,106 +47,107 @@
47 47

	
48 48
if HAVE_CLP
49 49
lemon_libemon_la_SOURCES += lemon/clp.cc
50 50
endif
51 51

	
52 52
if HAVE_CBC
53 53
lemon_libemon_la_SOURCES += lemon/cbc.cc
54 54
endif
55 55

	
56 56
lemon_HEADERS += \
57 57
	lemon/adaptors.h \
58 58
	lemon/arg_parser.h \
59 59
	lemon/assert.h \
60 60
	lemon/bellman_ford.h \
61 61
	lemon/bfs.h \
62 62
	lemon/bin_heap.h \
63 63
	lemon/binomial_heap.h \
64 64
	lemon/bucket_heap.h \
65 65
	lemon/capacity_scaling.h \
66 66
	lemon/cbc.h \
67 67
	lemon/circulation.h \
68 68
	lemon/clp.h \
69 69
	lemon/color.h \
70 70
	lemon/concept_check.h \
71 71
	lemon/connectivity.h \
72 72
	lemon/core.h \
73 73
	lemon/cost_scaling.h \
74 74
	lemon/counter.h \
75 75
	lemon/cplex.h \
76 76
	lemon/cycle_canceling.h \
77 77
	lemon/dfs.h \
78 78
	lemon/dheap.h \
79 79
	lemon/dijkstra.h \
80 80
	lemon/dim2.h \
81 81
	lemon/dimacs.h \
82 82
	lemon/edge_set.h \
83 83
	lemon/elevator.h \
84 84
	lemon/error.h \
85 85
	lemon/euler.h \
86 86
	lemon/fib_heap.h \
87 87
	lemon/fractional_matching.h \
88 88
	lemon/full_graph.h \
89 89
	lemon/glpk.h \
90 90
	lemon/gomory_hu.h \
91 91
	lemon/graph_to_eps.h \
92 92
	lemon/grid_graph.h \
93 93
	lemon/grosso_locatelli_pullan_mc.h \
94 94
	lemon/hartmann_orlin_mmc.h \
95 95
	lemon/howard_mmc.h \
96 96
	lemon/hypercube_graph.h \
97 97
	lemon/karp_mmc.h \
98 98
	lemon/kruskal.h \
99 99
	lemon/hao_orlin.h \
100 100
	lemon/lgf_reader.h \
101 101
	lemon/lgf_writer.h \
102 102
	lemon/list_graph.h \
103 103
	lemon/lp.h \
104 104
	lemon/lp_base.h \
105 105
	lemon/lp_skeleton.h \
106 106
	lemon/maps.h \
107 107
	lemon/matching.h \
108 108
	lemon/math.h \
109 109
	lemon/min_cost_arborescence.h \
110 110
	lemon/max_cardinality_search.h \
111
	lemon/nagamochi_ibaraki.h \
111 112
	lemon/nauty_reader.h \
112 113
	lemon/network_simplex.h \
113 114
	lemon/pairing_heap.h \
114 115
	lemon/path.h \
115 116
	lemon/planarity.h \
116 117
	lemon/preflow.h \
117 118
	lemon/quad_heap.h \
118 119
	lemon/radix_heap.h \
119 120
	lemon/radix_sort.h \
120 121
	lemon/random.h \
121 122
	lemon/smart_graph.h \
122 123
	lemon/soplex.h \
123 124
	lemon/static_graph.h \
124 125
	lemon/suurballe.h \
125 126
	lemon/time_measure.h \
126 127
	lemon/tolerance.h \
127 128
	lemon/unionfind.h \
128 129
	lemon/bits/windows.h
129 130

	
130 131
bits_HEADERS += \
131 132
	lemon/bits/alteration_notifier.h \
132 133
	lemon/bits/array_map.h \
133 134
	lemon/bits/bezier.h \
134 135
	lemon/bits/default_map.h \
135 136
	lemon/bits/edge_set_extender.h \
136 137
	lemon/bits/enable_if.h \
137 138
	lemon/bits/graph_adaptor_extender.h \
138 139
	lemon/bits/graph_extender.h \
139 140
	lemon/bits/map_extender.h \
140 141
	lemon/bits/path_dump.h \
141 142
	lemon/bits/solver_bits.h \
142 143
	lemon/bits/traits.h \
143 144
	lemon/bits/variant.h \
144 145
	lemon/bits/vector_map.h
145 146

	
146 147
concept_HEADERS += \
147 148
	lemon/concepts/digraph.h \
148 149
	lemon/concepts/graph.h \
149 150
	lemon/concepts/graph_components.h \
150 151
	lemon/concepts/heap.h \
151 152
	lemon/concepts/maps.h \
152 153
	lemon/concepts/path.h
Show white space 128 line context
1 1
/* -*- mode: C++; indent-tabs-mode: nil; -*-
2 2
 *
3 3
 * This file is a part of LEMON, a generic C++ optimization library.
4 4
 *
5 5
 * Copyright (C) 2003-2010
6 6
 * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
7 7
 * (Egervary Research Group on Combinatorial Optimization, EGRES).
8 8
 *
9 9
 * Permission to use, modify and distribute this software is granted
10 10
 * provided that this copyright notice appears in all copies. For
11 11
 * precise terms see the accompanying LICENSE file.
12 12
 *
13 13
 * This software is provided "AS IS" with no warranty of any kind,
14 14
 * express or implied, and with no claim as to its suitability for any
15 15
 * purpose.
16 16
 *
17 17
 */
18 18

	
19 19
#ifndef LEMON_HAO_ORLIN_H
20 20
#define LEMON_HAO_ORLIN_H
21 21

	
22 22
#include <vector>
23 23
#include <list>
24 24
#include <limits>
25 25

	
26 26
#include <lemon/maps.h>
27 27
#include <lemon/core.h>
28 28
#include <lemon/tolerance.h>
29 29

	
30 30
/// \file
31 31
/// \ingroup min_cut
32 32
/// \brief Implementation of the Hao-Orlin algorithm.
33 33
///
34 34
/// Implementation of the Hao-Orlin algorithm for finding a minimum cut
35 35
/// in a digraph.
36 36

	
37 37
namespace lemon {
38 38

	
39 39
  /// \ingroup min_cut
40 40
  ///
41 41
  /// \brief Hao-Orlin algorithm for finding a minimum cut in a digraph.
42 42
  ///
43 43
  /// This class implements the Hao-Orlin algorithm for finding a minimum
44 44
  /// value cut in a directed graph \f$D=(V,A)\f$.
45 45
  /// It takes a fixed node \f$ source \in V \f$ and
46 46
  /// consists of two phases: in the first phase it determines a
47 47
  /// minimum cut with \f$ source \f$ on the source-side (i.e. a set
48 48
  /// \f$ X\subsetneq V \f$ with \f$ source \in X \f$ and minimal outgoing
49 49
  /// capacity) and in the second phase it determines a minimum cut
50 50
  /// with \f$ source \f$ on the sink-side (i.e. a set
51 51
  /// \f$ X\subsetneq V \f$ with \f$ source \notin X \f$ and minimal outgoing
52 52
  /// capacity). Obviously, the smaller of these two cuts will be a
53 53
  /// minimum cut of \f$ D \f$. The algorithm is a modified
54 54
  /// preflow push-relabel algorithm. Our implementation calculates
55 55
  /// the minimum cut in \f$ O(n^2\sqrt{m}) \f$ time (we use the
56
  /// highest-label rule), or in \f$O(nm)\f$ for unit capacities. The
57
  /// purpose of such algorithm is e.g. testing network reliability.
56
  /// highest-label rule), or in \f$O(nm)\f$ for unit capacities. A notable
57
  /// use of this algorithm is testing network reliability.
58 58
  ///
59 59
  /// For an undirected graph you can run just the first phase of the
60 60
  /// algorithm or you can use the algorithm of Nagamochi and Ibaraki,
61 61
  /// which solves the undirected problem in \f$ O(nm + n^2 \log n) \f$
62 62
  /// time. It is implemented in the NagamochiIbaraki algorithm class.
63 63
  ///
64 64
  /// \tparam GR The type of the digraph the algorithm runs on.
65 65
  /// \tparam CAP The type of the arc map containing the capacities,
66 66
  /// which can be any numreric type. The default map type is
67 67
  /// \ref concepts::Digraph::ArcMap "GR::ArcMap<int>".
68 68
  /// \tparam TOL Tolerance class for handling inexact computations. The
69 69
  /// default tolerance type is \ref Tolerance "Tolerance<CAP::Value>".
70 70
#ifdef DOXYGEN
71 71
  template <typename GR, typename CAP, typename TOL>
72 72
#else
73 73
  template <typename GR,
74 74
            typename CAP = typename GR::template ArcMap<int>,
75 75
            typename TOL = Tolerance<typename CAP::Value> >
76 76
#endif
77 77
  class HaoOrlin {
78 78
  public:
79 79

	
80 80
    /// The digraph type of the algorithm
81 81
    typedef GR Digraph;
82 82
    /// The capacity map type of the algorithm
83 83
    typedef CAP CapacityMap;
84 84
    /// The tolerance type of the algorithm
85 85
    typedef TOL Tolerance;
86 86

	
87 87
  private:
88 88

	
89 89
    typedef typename CapacityMap::Value Value;
90 90

	
91 91
    TEMPLATE_DIGRAPH_TYPEDEFS(Digraph);
92 92

	
93 93
    const Digraph& _graph;
94 94
    const CapacityMap* _capacity;
95 95

	
96 96
    typedef typename Digraph::template ArcMap<Value> FlowMap;
97 97
    FlowMap* _flow;
98 98

	
99 99
    Node _source;
100 100

	
101 101
    int _node_num;
102 102

	
103 103
    // Bucketing structure
104 104
    std::vector<Node> _first, _last;
105 105
    typename Digraph::template NodeMap<Node>* _next;
106 106
    typename Digraph::template NodeMap<Node>* _prev;
107 107
    typename Digraph::template NodeMap<bool>* _active;
108 108
    typename Digraph::template NodeMap<int>* _bucket;
109 109

	
110 110
    std::vector<bool> _dormant;
111 111

	
112 112
    std::list<std::list<int> > _sets;
113 113
    std::list<int>::iterator _highest;
114 114

	
115 115
    typedef typename Digraph::template NodeMap<Value> ExcessMap;
116 116
    ExcessMap* _excess;
117 117

	
118 118
    typedef typename Digraph::template NodeMap<bool> SourceSetMap;
119 119
    SourceSetMap* _source_set;
120 120

	
121 121
    Value _min_cut;
... ...
@@ -851,155 +851,165 @@
851 851

	
852 852
    /// @{
853 853

	
854 854
    /// \brief Initialize the internal data structures.
855 855
    ///
856 856
    /// This function initializes the internal data structures. It creates
857 857
    /// the maps and some bucket structures for the algorithm.
858 858
    /// The first node is used as the source node for the push-relabel
859 859
    /// algorithm.
860 860
    void init() {
861 861
      init(NodeIt(_graph));
862 862
    }
863 863

	
864 864
    /// \brief Initialize the internal data structures.
865 865
    ///
866 866
    /// This function initializes the internal data structures. It creates
867 867
    /// the maps and some bucket structures for the algorithm.
868 868
    /// The given node is used as the source node for the push-relabel
869 869
    /// algorithm.
870 870
    void init(const Node& source) {
871 871
      _source = source;
872 872

	
873 873
      _node_num = countNodes(_graph);
874 874

	
875 875
      _first.resize(_node_num);
876 876
      _last.resize(_node_num);
877 877

	
878 878
      _dormant.resize(_node_num);
879 879

	
880 880
      if (!_flow) {
881 881
        _flow = new FlowMap(_graph);
882 882
      }
883 883
      if (!_next) {
884 884
        _next = new typename Digraph::template NodeMap<Node>(_graph);
885 885
      }
886 886
      if (!_prev) {
887 887
        _prev = new typename Digraph::template NodeMap<Node>(_graph);
888 888
      }
889 889
      if (!_active) {
890 890
        _active = new typename Digraph::template NodeMap<bool>(_graph);
891 891
      }
892 892
      if (!_bucket) {
893 893
        _bucket = new typename Digraph::template NodeMap<int>(_graph);
894 894
      }
895 895
      if (!_excess) {
896 896
        _excess = new ExcessMap(_graph);
897 897
      }
898 898
      if (!_source_set) {
899 899
        _source_set = new SourceSetMap(_graph);
900 900
      }
901 901
      if (!_min_cut_map) {
902 902
        _min_cut_map = new MinCutMap(_graph);
903 903
      }
904 904

	
905 905
      _min_cut = std::numeric_limits<Value>::max();
906 906
    }
907 907

	
908 908

	
909 909
    /// \brief Calculate a minimum cut with \f$ source \f$ on the
910 910
    /// source-side.
911 911
    ///
912 912
    /// This function calculates a minimum cut with \f$ source \f$ on the
913 913
    /// source-side (i.e. a set \f$ X\subsetneq V \f$ with
914 914
    /// \f$ source \in X \f$ and minimal outgoing capacity).
915
    /// It updates the stored cut if (and only if) the newly found one
916
    /// is better.
915 917
    ///
916 918
    /// \pre \ref init() must be called before using this function.
917 919
    void calculateOut() {
918 920
      findMinCutOut();
919 921
    }
920 922

	
921 923
    /// \brief Calculate a minimum cut with \f$ source \f$ on the
922 924
    /// sink-side.
923 925
    ///
924 926
    /// This function calculates a minimum cut with \f$ source \f$ on the
925 927
    /// sink-side (i.e. a set \f$ X\subsetneq V \f$ with
926 928
    /// \f$ source \notin X \f$ and minimal outgoing capacity).
929
    /// It updates the stored cut if (and only if) the newly found one
930
    /// is better.
927 931
    ///
928 932
    /// \pre \ref init() must be called before using this function.
929 933
    void calculateIn() {
930 934
      findMinCutIn();
931 935
    }
932 936

	
933 937

	
934 938
    /// \brief Run the algorithm.
935 939
    ///
936
    /// This function runs the algorithm. It finds nodes \c source and
937
    /// \c target arbitrarily and then calls \ref init(), \ref calculateOut()
940
    /// This function runs the algorithm. It chooses source node,
941
    /// then calls \ref init(), \ref calculateOut()
938 942
    /// and \ref calculateIn().
939 943
    void run() {
940 944
      init();
941 945
      calculateOut();
942 946
      calculateIn();
943 947
    }
944 948

	
945 949
    /// \brief Run the algorithm.
946 950
    ///
947
    /// This function runs the algorithm. It uses the given \c source node,
948
    /// finds a proper \c target node and then calls the \ref init(),
949
    /// \ref calculateOut() and \ref calculateIn().
951
    /// This function runs the algorithm. It calls \ref init(),
952
    /// \ref calculateOut() and \ref calculateIn() with the given
953
    /// source node.
950 954
    void run(const Node& s) {
951 955
      init(s);
952 956
      calculateOut();
953 957
      calculateIn();
954 958
    }
955 959

	
956 960
    /// @}
957 961

	
958 962
    /// \name Query Functions
959 963
    /// The result of the %HaoOrlin algorithm
960 964
    /// can be obtained using these functions.\n
961 965
    /// \ref run(), \ref calculateOut() or \ref calculateIn()
962 966
    /// should be called before using them.
963 967

	
964 968
    /// @{
965 969

	
966 970
    /// \brief Return the value of the minimum cut.
967 971
    ///
968
    /// This function returns the value of the minimum cut.
972
    /// This function returns the value of the best cut found by the
973
    /// previously called \ref run(), \ref calculateOut() or \ref
974
    /// calculateIn().
969 975
    ///
970 976
    /// \pre \ref run(), \ref calculateOut() or \ref calculateIn()
971 977
    /// must be called before using this function.
972 978
    Value minCutValue() const {
973 979
      return _min_cut;
974 980
    }
975 981

	
976 982

	
977 983
    /// \brief Return a minimum cut.
978 984
    ///
979
    /// This function sets \c cutMap to the characteristic vector of a
980
    /// minimum value cut: it will give a non-empty set \f$ X\subsetneq V \f$
981
    /// with minimal outgoing capacity (i.e. \c cutMap will be \c true exactly
985
    /// This function gives the best cut found by the
986
    /// previously called \ref run(), \ref calculateOut() or \ref
987
    /// calculateIn().
988
    ///
989
    /// It sets \c cutMap to the characteristic vector of the found
990
    /// minimum value cut - a non-empty set \f$ X\subsetneq V \f$
991
    /// of minimum outgoing capacity (i.e. \c cutMap will be \c true exactly
982 992
    /// for the nodes of \f$ X \f$).
983 993
    ///
984 994
    /// \param cutMap A \ref concepts::WriteMap "writable" node map with
985 995
    /// \c bool (or convertible) value type.
986 996
    ///
987 997
    /// \return The value of the minimum cut.
988 998
    ///
989 999
    /// \pre \ref run(), \ref calculateOut() or \ref calculateIn()
990 1000
    /// must be called before using this function.
991 1001
    template <typename CutMap>
992 1002
    Value minCutMap(CutMap& cutMap) const {
993 1003
      for (NodeIt it(_graph); it != INVALID; ++it) {
994 1004
        cutMap.set(it, (*_min_cut_map)[it]);
995 1005
      }
996 1006
      return _min_cut;
997 1007
    }
998 1008

	
999 1009
    /// @}
1000 1010

	
1001 1011
  }; //class HaoOrlin
1002 1012

	
1003 1013
} //namespace lemon
1004 1014

	
1005 1015
#endif //LEMON_HAO_ORLIN_H
Show white space 128 line context
1 1
INCLUDE_DIRECTORIES(
2 2
  ${PROJECT_SOURCE_DIR}
3 3
  ${PROJECT_BINARY_DIR}
4 4
)
5 5

	
6 6
LINK_DIRECTORIES(
7 7
  ${PROJECT_BINARY_DIR}/lemon
8 8
)
9 9

	
10 10
SET(TESTS
11 11
  adaptors_test
12 12
  bellman_ford_test
13 13
  bfs_test
14 14
  circulation_test
15 15
  connectivity_test
16 16
  counter_test
17 17
  dfs_test
18 18
  digraph_test
19 19
  dijkstra_test
20 20
  dim_test
21 21
  edge_set_test
22 22
  error_test
23 23
  euler_test
24 24
  fractional_matching_test
25 25
  gomory_hu_test
26 26
  graph_copy_test
27 27
  graph_test
28 28
  graph_utils_test
29 29
  hao_orlin_test
30 30
  heap_test
31 31
  kruskal_test
32 32
  maps_test
33 33
  matching_test
34 34
  max_cardinality_search_test
35 35
  max_clique_test
36 36
  min_cost_arborescence_test
37 37
  min_cost_flow_test
38 38
  min_mean_cycle_test
39
  nagamochi_ibaraki_test
39 40
  path_test
40 41
  planarity_test
41 42
  preflow_test
42 43
  radix_sort_test
43 44
  random_test
44 45
  suurballe_test
45 46
  time_measure_test
46 47
  unionfind_test
47 48
)
48 49

	
49 50
IF(LEMON_HAVE_LP)
51
  IF(${CMAKE_BUILD_TYPE} STREQUAL "Maintainer")
50 52
  ADD_EXECUTABLE(lp_test lp_test.cc)
53
  ELSE()
54
    ADD_EXECUTABLE(lp_test EXCLUDE_FROM_ALL lp_test.cc)
55
  ENDIF()
56

	
51 57
  SET(LP_TEST_LIBS lemon)
52 58

	
53 59
  IF(LEMON_HAVE_GLPK)
54 60
    SET(LP_TEST_LIBS ${LP_TEST_LIBS} ${GLPK_LIBRARIES})
55 61
  ENDIF()
56 62
  IF(LEMON_HAVE_CPLEX)
57 63
    SET(LP_TEST_LIBS ${LP_TEST_LIBS} ${CPLEX_LIBRARIES})
58 64
  ENDIF()
59 65
  IF(LEMON_HAVE_CLP)
60 66
    SET(LP_TEST_LIBS ${LP_TEST_LIBS} ${COIN_CLP_LIBRARIES})
61 67
  ENDIF()
62 68

	
63 69
  TARGET_LINK_LIBRARIES(lp_test ${LP_TEST_LIBS})
64 70
  ADD_TEST(lp_test lp_test)
65 71

	
66 72
  IF(WIN32 AND LEMON_HAVE_GLPK)
67 73
    GET_TARGET_PROPERTY(TARGET_LOC lp_test LOCATION)
68 74
    GET_FILENAME_COMPONENT(TARGET_PATH ${TARGET_LOC} PATH)
69 75
    ADD_CUSTOM_COMMAND(TARGET lp_test POST_BUILD
70 76
      COMMAND ${CMAKE_COMMAND} -E copy ${GLPK_BIN_DIR}/glpk.dll ${TARGET_PATH}
71 77
      COMMAND ${CMAKE_COMMAND} -E copy ${GLPK_BIN_DIR}/libltdl3.dll ${TARGET_PATH}
72 78
      COMMAND ${CMAKE_COMMAND} -E copy ${GLPK_BIN_DIR}/zlib1.dll ${TARGET_PATH}
73 79
    )
74 80
  ENDIF()
75 81

	
76 82
  IF(WIN32 AND LEMON_HAVE_CPLEX)
77 83
    GET_TARGET_PROPERTY(TARGET_LOC lp_test LOCATION)
78 84
    GET_FILENAME_COMPONENT(TARGET_PATH ${TARGET_LOC} PATH)
79 85
    ADD_CUSTOM_COMMAND(TARGET lp_test POST_BUILD
80 86
      COMMAND ${CMAKE_COMMAND} -E copy ${CPLEX_BIN_DIR}/cplex91.dll ${TARGET_PATH}
81 87
    )
82 88
  ENDIF()
83 89
ENDIF()
84 90

	
85 91
IF(LEMON_HAVE_MIP)
92
  IF(${CMAKE_BUILD_TYPE} STREQUAL "Maintainer")
86 93
  ADD_EXECUTABLE(mip_test mip_test.cc)
94
  ELSE()
95
    ADD_EXECUTABLE(mip_test EXCLUDE_FROM_ALL mip_test.cc)
96
  ENDIF()
97

	
87 98
  SET(MIP_TEST_LIBS lemon)
88 99

	
89 100
  IF(LEMON_HAVE_GLPK)
90 101
    SET(MIP_TEST_LIBS ${MIP_TEST_LIBS} ${GLPK_LIBRARIES})
91 102
  ENDIF()
92 103
  IF(LEMON_HAVE_CPLEX)
93 104
    SET(MIP_TEST_LIBS ${MIP_TEST_LIBS} ${CPLEX_LIBRARIES})
94 105
  ENDIF()
95 106
  IF(LEMON_HAVE_CBC)
96 107
    SET(MIP_TEST_LIBS ${MIP_TEST_LIBS} ${COIN_CBC_LIBRARIES})
97 108
  ENDIF()
98 109

	
99 110
  TARGET_LINK_LIBRARIES(mip_test ${MIP_TEST_LIBS})
100 111
  ADD_TEST(mip_test mip_test)
101 112

	
102 113
  IF(WIN32 AND LEMON_HAVE_GLPK)
103 114
    GET_TARGET_PROPERTY(TARGET_LOC mip_test LOCATION)
104 115
    GET_FILENAME_COMPONENT(TARGET_PATH ${TARGET_LOC} PATH)
105 116
    ADD_CUSTOM_COMMAND(TARGET mip_test POST_BUILD
106 117
      COMMAND ${CMAKE_COMMAND} -E copy ${GLPK_BIN_DIR}/glpk.dll ${TARGET_PATH}
107 118
      COMMAND ${CMAKE_COMMAND} -E copy ${GLPK_BIN_DIR}/libltdl3.dll ${TARGET_PATH}
108 119
      COMMAND ${CMAKE_COMMAND} -E copy ${GLPK_BIN_DIR}/zlib1.dll ${TARGET_PATH}
109 120
    )
110 121
  ENDIF()
111 122

	
112 123
  IF(WIN32 AND LEMON_HAVE_CPLEX)
113 124
    GET_TARGET_PROPERTY(TARGET_LOC mip_test LOCATION)
114 125
    GET_FILENAME_COMPONENT(TARGET_PATH ${TARGET_LOC} PATH)
115 126
    ADD_CUSTOM_COMMAND(TARGET mip_test POST_BUILD
116 127
      COMMAND ${CMAKE_COMMAND} -E copy ${CPLEX_BIN_DIR}/cplex91.dll ${TARGET_PATH}
117 128
    )
118 129
  ENDIF()
119 130
ENDIF()
120 131

	
121 132
FOREACH(TEST_NAME ${TESTS})
122 133
  IF(${CMAKE_BUILD_TYPE} STREQUAL "Maintainer")
123 134
    ADD_EXECUTABLE(${TEST_NAME} ${TEST_NAME}.cc)
124 135
  ELSE()
125 136
    ADD_EXECUTABLE(${TEST_NAME} EXCLUDE_FROM_ALL ${TEST_NAME}.cc)
126 137
  ENDIF()
127 138
  TARGET_LINK_LIBRARIES(${TEST_NAME} lemon)
128 139
  ADD_TEST(${TEST_NAME} ${TEST_NAME})
129 140
  ADD_DEPENDENCIES(check ${TEST_NAME})
130 141
ENDFOREACH()
Show white space 128 line context
1 1
if USE_VALGRIND
2 2
TESTS_ENVIRONMENT=$(top_srcdir)/scripts/valgrind-wrapper.sh
3 3
endif
4 4

	
5 5
EXTRA_DIST += \
6 6
	test/CMakeLists.txt
7 7

	
8 8
noinst_HEADERS += \
9 9
	test/graph_test.h \
10 10
	test/test_tools.h
11 11

	
12 12
check_PROGRAMS += \
13 13
	test/adaptors_test \
14 14
	test/bellman_ford_test \
15 15
	test/bfs_test \
16 16
	test/circulation_test \
17 17
	test/connectivity_test \
18 18
	test/counter_test \
19 19
	test/dfs_test \
20 20
	test/digraph_test \
21 21
	test/dijkstra_test \
22 22
	test/dim_test \
23 23
	test/edge_set_test \
24 24
	test/error_test \
25 25
	test/euler_test \
26 26
	test/fractional_matching_test \
27 27
	test/gomory_hu_test \
28 28
	test/graph_copy_test \
29 29
	test/graph_test \
30 30
	test/graph_utils_test \
31 31
	test/hao_orlin_test \
32 32
	test/heap_test \
33 33
	test/kruskal_test \
34 34
	test/maps_test \
35 35
	test/matching_test \
36 36
	test/max_cardinality_search_test \
37 37
	test/max_clique_test \
38 38
	test/min_cost_arborescence_test \
39 39
	test/min_cost_flow_test \
40 40
	test/min_mean_cycle_test \
41
	test/nagamochi_ibaraki_test \
41 42
	test/path_test \
42 43
	test/planarity_test \
43 44
	test/preflow_test \
44 45
	test/radix_sort_test \
45 46
	test/random_test \
46 47
	test/suurballe_test \
47 48
	test/test_tools_fail \
48 49
	test/test_tools_pass \
49 50
	test/time_measure_test \
50 51
	test/unionfind_test
51 52

	
52 53
test_test_tools_pass_DEPENDENCIES = demo
53 54

	
54 55
if HAVE_LP
55 56
check_PROGRAMS += test/lp_test
56 57
endif HAVE_LP
57 58
if HAVE_MIP
58 59
check_PROGRAMS += test/mip_test
59 60
endif HAVE_MIP
60 61

	
61 62
TESTS += $(check_PROGRAMS)
62 63
XFAIL_TESTS += test/test_tools_fail$(EXEEXT)
63 64

	
64 65
test_adaptors_test_SOURCES = test/adaptors_test.cc
65 66
test_bellman_ford_test_SOURCES = test/bellman_ford_test.cc
66 67
test_bfs_test_SOURCES = test/bfs_test.cc
67 68
test_circulation_test_SOURCES = test/circulation_test.cc
68 69
test_counter_test_SOURCES = test/counter_test.cc
69 70
test_connectivity_test_SOURCES = test/connectivity_test.cc
70 71
test_dfs_test_SOURCES = test/dfs_test.cc
71 72
test_digraph_test_SOURCES = test/digraph_test.cc
72 73
test_dijkstra_test_SOURCES = test/dijkstra_test.cc
73 74
test_dim_test_SOURCES = test/dim_test.cc
74 75
test_edge_set_test_SOURCES = test/edge_set_test.cc
75 76
test_error_test_SOURCES = test/error_test.cc
76 77
test_euler_test_SOURCES = test/euler_test.cc
77 78
test_fractional_matching_test_SOURCES = test/fractional_matching_test.cc
78 79
test_gomory_hu_test_SOURCES = test/gomory_hu_test.cc
79 80
test_graph_copy_test_SOURCES = test/graph_copy_test.cc
80 81
test_graph_test_SOURCES = test/graph_test.cc
81 82
test_graph_utils_test_SOURCES = test/graph_utils_test.cc
82 83
test_heap_test_SOURCES = test/heap_test.cc
83 84
test_kruskal_test_SOURCES = test/kruskal_test.cc
84 85
test_hao_orlin_test_SOURCES = test/hao_orlin_test.cc
85 86
test_lp_test_SOURCES = test/lp_test.cc
86 87
test_maps_test_SOURCES = test/maps_test.cc
87 88
test_mip_test_SOURCES = test/mip_test.cc
88 89
test_matching_test_SOURCES = test/matching_test.cc
89 90
test_max_cardinality_search_test_SOURCES = test/max_cardinality_search_test.cc
90 91
test_max_clique_test_SOURCES = test/max_clique_test.cc
91 92
test_min_cost_arborescence_test_SOURCES = test/min_cost_arborescence_test.cc
92 93
test_min_cost_flow_test_SOURCES = test/min_cost_flow_test.cc
93 94
test_min_mean_cycle_test_SOURCES = test/min_mean_cycle_test.cc
95
test_nagamochi_ibaraki_test_SOURCES = test/nagamochi_ibaraki_test.cc
94 96
test_path_test_SOURCES = test/path_test.cc
95 97
test_planarity_test_SOURCES = test/planarity_test.cc
96 98
test_preflow_test_SOURCES = test/preflow_test.cc
97 99
test_radix_sort_test_SOURCES = test/radix_sort_test.cc
98 100
test_suurballe_test_SOURCES = test/suurballe_test.cc
99 101
test_random_test_SOURCES = test/random_test.cc
100 102
test_test_tools_fail_SOURCES = test/test_tools_fail.cc
101 103
test_test_tools_pass_SOURCES = test/test_tools_pass.cc
102 104
test_time_measure_test_SOURCES = test/time_measure_test.cc
103 105
test_unionfind_test_SOURCES = test/unionfind_test.cc
0 comments (0 inline)