lemon/max_cardinality_search.h
changeset 1020 70bee017b584
child 1129 9a3187204242
equal deleted inserted replaced
-1:000000000000 0:1213c65d8976
       
     1 /* -*- C++ -*-
       
     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_MAX_CARDINALITY_SEARCH_H
       
    20 #define LEMON_MAX_CARDINALITY_SEARCH_H
       
    21 
       
    22 
       
    23 /// \ingroup search
       
    24 /// \file 
       
    25 /// \brief Maximum cardinality search in undirected digraphs.
       
    26 
       
    27 #include <lemon/bin_heap.h>
       
    28 #include <lemon/bucket_heap.h>
       
    29 
       
    30 #include <lemon/error.h>
       
    31 #include <lemon/maps.h>
       
    32 
       
    33 #include <functional>
       
    34 
       
    35 namespace lemon {
       
    36 
       
    37   /// \brief Default traits class of MaxCardinalitySearch class.
       
    38   ///
       
    39   /// Default traits class of MaxCardinalitySearch class.
       
    40   /// \param Digraph Digraph type.
       
    41   /// \param CapacityMap Type of capacity map.
       
    42   template <typename GR, typename CAP>
       
    43   struct MaxCardinalitySearchDefaultTraits {
       
    44     /// The digraph type the algorithm runs on. 
       
    45     typedef GR Digraph;
       
    46 
       
    47     template <typename CM>
       
    48     struct CapMapSelector {
       
    49 
       
    50       typedef CM CapacityMap;
       
    51 
       
    52       static CapacityMap *createCapacityMap(const Digraph& g) {
       
    53 	return new CapacityMap(g);
       
    54       }
       
    55     };
       
    56 
       
    57     template <typename CM>
       
    58     struct CapMapSelector<ConstMap<CM, Const<int, 1> > > {
       
    59 
       
    60       typedef ConstMap<CM, Const<int, 1> > CapacityMap;
       
    61 
       
    62       static CapacityMap *createCapacityMap(const Digraph&) {
       
    63 	return new CapacityMap;
       
    64       }
       
    65     };
       
    66 
       
    67     /// \brief The type of the map that stores the arc capacities.
       
    68     ///
       
    69     /// The type of the map that stores the arc capacities.
       
    70     /// It must meet the \ref concepts::ReadMap "ReadMap" concept.
       
    71     typedef typename CapMapSelector<CAP>::CapacityMap CapacityMap;
       
    72 
       
    73     /// \brief The type of the capacity of the arcs.
       
    74     typedef typename CapacityMap::Value Value;
       
    75 
       
    76     /// \brief Instantiates a CapacityMap.
       
    77     ///
       
    78     /// This function instantiates a \ref CapacityMap.
       
    79     /// \param digraph is the digraph, to which we would like to define
       
    80     /// the CapacityMap.
       
    81     static CapacityMap *createCapacityMap(const Digraph& digraph) {
       
    82       return CapMapSelector<CapacityMap>::createCapacityMap(digraph);
       
    83     }
       
    84 
       
    85     /// \brief The cross reference type used by heap.
       
    86     ///
       
    87     /// The cross reference type used by heap.
       
    88     /// Usually it is \c Digraph::NodeMap<int>.
       
    89     typedef typename Digraph::template NodeMap<int> HeapCrossRef;
       
    90 
       
    91     /// \brief Instantiates a HeapCrossRef.
       
    92     ///
       
    93     /// This function instantiates a \ref HeapCrossRef. 
       
    94     /// \param digraph is the digraph, to which we would like to define the 
       
    95     /// HeapCrossRef.
       
    96     static HeapCrossRef *createHeapCrossRef(const Digraph &digraph) {
       
    97       return new HeapCrossRef(digraph);
       
    98     }
       
    99     
       
   100     template <typename CapacityMap>
       
   101     struct HeapSelector {
       
   102       template <typename Value, typename Ref>
       
   103       struct Selector { 
       
   104         typedef BinHeap<Value, Ref, std::greater<Value> > Heap;
       
   105       };
       
   106     };
       
   107 
       
   108     template <typename CapacityKey>
       
   109     struct HeapSelector<ConstMap<CapacityKey, Const<int, 1> > > {
       
   110       template <typename Value, typename Ref>
       
   111       struct Selector {
       
   112         typedef BucketHeap<Ref, false > Heap;
       
   113       };
       
   114     };
       
   115 
       
   116     /// \brief The heap type used by MaxCardinalitySearch algorithm.
       
   117     ///
       
   118     /// The heap type used by MaxCardinalitySearch algorithm. It should
       
   119     /// maximalize the priorities. The default heap type is
       
   120     /// the \ref BinHeap, but it is specialized when the
       
   121     /// CapacityMap is ConstMap<Digraph::Node, Const<int, 1> >
       
   122     /// to BucketHeap.
       
   123     ///
       
   124     /// \sa MaxCardinalitySearch
       
   125     typedef typename HeapSelector<CapacityMap>
       
   126     ::template Selector<Value, HeapCrossRef>
       
   127     ::Heap Heap;
       
   128 
       
   129     /// \brief Instantiates a Heap.
       
   130     ///
       
   131     /// This function instantiates a \ref Heap. 
       
   132     /// \param crossref The cross reference of the heap.
       
   133     static Heap *createHeap(HeapCrossRef& crossref) {
       
   134       return new Heap(crossref);
       
   135     }
       
   136 
       
   137     /// \brief The type of the map that stores whether a node is processed.
       
   138     ///
       
   139     /// The type of the map that stores whether a node is processed.
       
   140     /// It must meet the \ref concepts::WriteMap "WriteMap" concept.
       
   141     /// By default it is a NullMap.
       
   142     typedef NullMap<typename Digraph::Node, bool> ProcessedMap;
       
   143 
       
   144     /// \brief Instantiates a ProcessedMap.
       
   145     ///
       
   146     /// This function instantiates a \ref ProcessedMap. 
       
   147     /// \param digraph is the digraph, to which
       
   148     /// we would like to define the \ref ProcessedMap
       
   149 #ifdef DOXYGEN
       
   150     static ProcessedMap *createProcessedMap(const Digraph &digraph)
       
   151 #else
       
   152     static ProcessedMap *createProcessedMap(const Digraph &)
       
   153 #endif
       
   154     {
       
   155       return new ProcessedMap();
       
   156     }
       
   157 
       
   158     /// \brief The type of the map that stores the cardinalities of the nodes.
       
   159     /// 
       
   160     /// The type of the map that stores the cardinalities of the nodes.
       
   161     /// It must meet the \ref concepts::WriteMap "WriteMap" concept.
       
   162     typedef typename Digraph::template NodeMap<Value> CardinalityMap;
       
   163 
       
   164     /// \brief Instantiates a CardinalityMap.
       
   165     ///
       
   166     /// This function instantiates a \ref CardinalityMap. 
       
   167     /// \param digraph is the digraph, to which we would like to define the \ref 
       
   168     /// CardinalityMap
       
   169     static CardinalityMap *createCardinalityMap(const Digraph &digraph) {
       
   170       return new CardinalityMap(digraph);
       
   171     }
       
   172 
       
   173 
       
   174   };
       
   175   
       
   176   /// \ingroup search
       
   177   ///
       
   178   /// \brief Maximum Cardinality Search algorithm class.
       
   179   ///
       
   180   /// This class provides an efficient implementation of Maximum Cardinality 
       
   181   /// Search algorithm. The maximum cardinality search first chooses any 
       
   182   /// node of the digraph. Then every time it chooses one unprocessed node
       
   183   /// with maximum cardinality, i.e the sum of capacities on out arcs to the nodes
       
   184   /// which were previusly processed.
       
   185   /// If there is a cut in the digraph the algorithm should choose
       
   186   /// again any unprocessed node of the digraph.
       
   187 
       
   188   /// The arc capacities are passed to the algorithm using a
       
   189   /// \ref concepts::ReadMap "ReadMap", so it is easy to change it to any 
       
   190   /// kind of capacity.
       
   191   ///
       
   192   /// The type of the capacity is determined by the \ref 
       
   193   /// concepts::ReadMap::Value "Value" of the capacity map.
       
   194   ///
       
   195   /// It is also possible to change the underlying priority heap.
       
   196   ///
       
   197   ///
       
   198   /// \param GR The digraph type the algorithm runs on. The value of
       
   199   /// Digraph is not used directly by the search algorithm, it 
       
   200   /// is only passed to \ref MaxCardinalitySearchDefaultTraits.
       
   201   /// \param CAP This read-only ArcMap determines the capacities of 
       
   202   /// the arcs. It is read once for each arc, so the map may involve in
       
   203   /// relatively time consuming process to compute the arc capacity if
       
   204   /// it is necessary. The default map type is \ref
       
   205   /// ConstMap "ConstMap<concepts::Digraph::Arc, Const<int,1> >". The value
       
   206   /// of CapacityMap is not used directly by search algorithm, it is only 
       
   207   /// passed to \ref MaxCardinalitySearchDefaultTraits.  
       
   208   /// \param TR Traits class to set various data types used by the 
       
   209   /// algorithm.  The default traits class is 
       
   210   /// \ref MaxCardinalitySearchDefaultTraits 
       
   211   /// "MaxCardinalitySearchDefaultTraits<GR, CAP>".  
       
   212   /// See \ref MaxCardinalitySearchDefaultTraits 
       
   213   /// for the documentation of a MaxCardinalitySearch traits class.
       
   214 
       
   215 #ifdef DOXYGEN
       
   216   template <typename GR, typename CAP, typename TR>
       
   217 #else
       
   218   template <typename GR, typename CAP = 
       
   219 	    ConstMap<typename GR::Arc, Const<int,1> >,
       
   220 	    typename TR = 
       
   221             MaxCardinalitySearchDefaultTraits<GR, CAP> >
       
   222 #endif
       
   223   class MaxCardinalitySearch {
       
   224   public:
       
   225 
       
   226     typedef TR Traits;
       
   227     ///The type of the underlying digraph.
       
   228     typedef typename Traits::Digraph Digraph;
       
   229     
       
   230     ///The type of the capacity of the arcs.
       
   231     typedef typename Traits::CapacityMap::Value Value;
       
   232     ///The type of the map that stores the arc capacities.
       
   233     typedef typename Traits::CapacityMap CapacityMap;
       
   234     ///The type of the map indicating if a node is processed.
       
   235     typedef typename Traits::ProcessedMap ProcessedMap;
       
   236     ///The type of the map that stores the cardinalities of the nodes.
       
   237     typedef typename Traits::CardinalityMap CardinalityMap;
       
   238     ///The cross reference type used for the current heap.
       
   239     typedef typename Traits::HeapCrossRef HeapCrossRef;
       
   240     ///The heap type used by the algorithm. It maximizes the priorities.
       
   241     typedef typename Traits::Heap Heap;
       
   242   private:
       
   243     // Pointer to the underlying digraph.
       
   244     const Digraph *_graph;
       
   245     // Pointer to the capacity map
       
   246     const CapacityMap *_capacity;
       
   247     // Indicates if \ref _capacity is locally allocated (\c true) or not.
       
   248     bool local_capacity;
       
   249     // Pointer to the map of cardinality.
       
   250     CardinalityMap *_cardinality;
       
   251     // Indicates if \ref _cardinality is locally allocated (\c true) or not.
       
   252     bool local_cardinality;
       
   253     // Pointer to the map of processed status of the nodes.
       
   254     ProcessedMap *_processed;
       
   255     // Indicates if \ref _processed is locally allocated (\c true) or not.
       
   256     bool local_processed;
       
   257     // Pointer to the heap cross references.
       
   258     HeapCrossRef *_heap_cross_ref;
       
   259     // Indicates if \ref _heap_cross_ref is locally allocated (\c true) or not.
       
   260     bool local_heap_cross_ref;
       
   261     // Pointer to the heap.
       
   262     Heap *_heap;
       
   263     // Indicates if \ref _heap is locally allocated (\c true) or not.
       
   264     bool local_heap;
       
   265 
       
   266   public :
       
   267 
       
   268     typedef MaxCardinalitySearch Create;
       
   269  
       
   270     ///\name Named template parameters
       
   271 
       
   272     ///@{
       
   273 
       
   274     template <class T>
       
   275     struct DefCapacityMapTraits : public Traits {
       
   276       typedef T CapacityMap;
       
   277       static CapacityMap *createCapacityMap(const Digraph &) {
       
   278        	LEMON_ASSERT(false,"Uninitialized parameter.");
       
   279 	return 0;
       
   280       }
       
   281     };
       
   282     /// \brief \ref named-templ-param "Named parameter" for setting 
       
   283     /// CapacityMap type
       
   284     ///
       
   285     /// \ref named-templ-param "Named parameter" for setting CapacityMap type
       
   286     /// for the algorithm.
       
   287     template <class T>
       
   288     struct SetCapacityMap 
       
   289       : public MaxCardinalitySearch<Digraph, CapacityMap, 
       
   290                                     DefCapacityMapTraits<T> > { 
       
   291       typedef MaxCardinalitySearch<Digraph, CapacityMap, 
       
   292                                    DefCapacityMapTraits<T> > Create;
       
   293     };
       
   294 
       
   295     template <class T>
       
   296     struct DefCardinalityMapTraits : public Traits {
       
   297       typedef T CardinalityMap;
       
   298       static CardinalityMap *createCardinalityMap(const Digraph &) 
       
   299       {
       
   300 	LEMON_ASSERT(false,"Uninitialized parameter.");
       
   301 	return 0;
       
   302       }
       
   303     };
       
   304     /// \brief \ref named-templ-param "Named parameter" for setting 
       
   305     /// CardinalityMap type
       
   306     ///
       
   307     /// \ref named-templ-param "Named parameter" for setting CardinalityMap 
       
   308     /// type for the algorithm.
       
   309     template <class T>
       
   310     struct SetCardinalityMap 
       
   311       : public MaxCardinalitySearch<Digraph, CapacityMap, 
       
   312                                     DefCardinalityMapTraits<T> > { 
       
   313       typedef MaxCardinalitySearch<Digraph, CapacityMap, 
       
   314                                    DefCardinalityMapTraits<T> > Create;
       
   315     };
       
   316     
       
   317     template <class T>
       
   318     struct DefProcessedMapTraits : public Traits {
       
   319       typedef T ProcessedMap;
       
   320       static ProcessedMap *createProcessedMap(const Digraph &) {
       
   321        	LEMON_ASSERT(false,"Uninitialized parameter.");
       
   322 	return 0;
       
   323       }
       
   324     };
       
   325     /// \brief \ref named-templ-param "Named parameter" for setting 
       
   326     /// ProcessedMap type
       
   327     ///
       
   328     /// \ref named-templ-param "Named parameter" for setting ProcessedMap type
       
   329     /// for the algorithm.
       
   330     template <class T>
       
   331     struct SetProcessedMap 
       
   332       : public MaxCardinalitySearch<Digraph, CapacityMap, 
       
   333                                     DefProcessedMapTraits<T> > { 
       
   334       typedef MaxCardinalitySearch<Digraph, CapacityMap, 
       
   335                                    DefProcessedMapTraits<T> > Create;
       
   336     };
       
   337     
       
   338     template <class H, class CR>
       
   339     struct DefHeapTraits : public Traits {
       
   340       typedef CR HeapCrossRef;
       
   341       typedef H Heap;
       
   342       static HeapCrossRef *createHeapCrossRef(const Digraph &) {
       
   343      	LEMON_ASSERT(false,"Uninitialized parameter.");
       
   344 	return 0;
       
   345       }
       
   346       static Heap *createHeap(HeapCrossRef &) {
       
   347        	LEMON_ASSERT(false,"Uninitialized parameter.");
       
   348 	return 0;
       
   349       }
       
   350     };
       
   351     /// \brief \ref named-templ-param "Named parameter" for setting heap 
       
   352     /// and cross reference type
       
   353     ///
       
   354     /// \ref named-templ-param "Named parameter" for setting heap and cross 
       
   355     /// reference type for the algorithm.
       
   356     template <class H, class CR = typename Digraph::template NodeMap<int> >
       
   357     struct SetHeap
       
   358       : public MaxCardinalitySearch<Digraph, CapacityMap, 
       
   359                                     DefHeapTraits<H, CR> > { 
       
   360       typedef MaxCardinalitySearch< Digraph, CapacityMap, 
       
   361                                     DefHeapTraits<H, CR> > Create;
       
   362     };
       
   363 
       
   364     template <class H, class CR>
       
   365     struct DefStandardHeapTraits : public Traits {
       
   366       typedef CR HeapCrossRef;
       
   367       typedef H Heap;
       
   368       static HeapCrossRef *createHeapCrossRef(const Digraph &digraph) {
       
   369 	return new HeapCrossRef(digraph);
       
   370       }
       
   371       static Heap *createHeap(HeapCrossRef &crossref) {
       
   372 	return new Heap(crossref);
       
   373       }
       
   374     };
       
   375 
       
   376     /// \brief \ref named-templ-param "Named parameter" for setting heap and 
       
   377     /// cross reference type with automatic allocation
       
   378     ///
       
   379     /// \ref named-templ-param "Named parameter" for setting heap and cross 
       
   380     /// reference type. It can allocate the heap and the cross reference 
       
   381     /// object if the cross reference's constructor waits for the digraph as 
       
   382     /// parameter and the heap's constructor waits for the cross reference.
       
   383     template <class H, class CR = typename Digraph::template NodeMap<int> >
       
   384     struct SetStandardHeap
       
   385       : public MaxCardinalitySearch<Digraph, CapacityMap, 
       
   386                                     DefStandardHeapTraits<H, CR> > { 
       
   387       typedef MaxCardinalitySearch<Digraph, CapacityMap, 
       
   388                                    DefStandardHeapTraits<H, CR> > 
       
   389       Create;
       
   390     };
       
   391     
       
   392     ///@}
       
   393 
       
   394 
       
   395   protected:
       
   396 
       
   397     MaxCardinalitySearch() {}
       
   398 
       
   399   public:      
       
   400     
       
   401     /// \brief Constructor.
       
   402     ///
       
   403     ///\param digraph the digraph the algorithm will run on.
       
   404     ///\param capacity the capacity map used by the algorithm.
       
   405     ///When no capacity map given, a constant 1 capacity map will
       
   406     ///be allocated.
       
   407 #ifdef DOXYGEN
       
   408     MaxCardinalitySearch(const Digraph& digraph,
       
   409 			 const CapacityMap& capacity=0 ) :
       
   410 #else
       
   411     MaxCardinalitySearch(const Digraph& digraph,
       
   412 			 const CapacityMap& capacity=*static_cast<const CapacityMap*>(0) ) :
       
   413 #endif
       
   414       _graph(&digraph),
       
   415       _capacity(&capacity), local_capacity(false),
       
   416       _cardinality(0), local_cardinality(false),
       
   417       _processed(0), local_processed(false),
       
   418       _heap_cross_ref(0), local_heap_cross_ref(false),
       
   419       _heap(0), local_heap(false)
       
   420     { }
       
   421 
       
   422     /// \brief Destructor.
       
   423     ~MaxCardinalitySearch() {
       
   424       if(local_capacity) delete _capacity;
       
   425       if(local_cardinality) delete _cardinality;
       
   426       if(local_processed) delete _processed;
       
   427       if(local_heap_cross_ref) delete _heap_cross_ref;
       
   428       if(local_heap) delete _heap;
       
   429     }
       
   430 
       
   431     /// \brief Sets the capacity map.
       
   432     ///
       
   433     /// Sets the capacity map.
       
   434     /// \return <tt> (*this) </tt>
       
   435     MaxCardinalitySearch &capacityMap(const CapacityMap &m) {
       
   436       if (local_capacity) {
       
   437 	delete _capacity;
       
   438 	local_capacity=false;
       
   439       }
       
   440       _capacity=&m;
       
   441       return *this;
       
   442     }
       
   443 
       
   444     /// \brief Returns a const reference to the capacity map.
       
   445     ///
       
   446     /// Returns a const reference to the capacity map used by
       
   447     /// the algorithm.
       
   448     const CapacityMap &capacityMap() const {
       
   449       return *_capacity;
       
   450     }
       
   451 
       
   452     /// \brief Sets the map storing the cardinalities calculated by the 
       
   453     /// algorithm.
       
   454     ///
       
   455     /// Sets the map storing the cardinalities calculated by the algorithm.
       
   456     /// If you don't use this function before calling \ref run(),
       
   457     /// it will allocate one. The destuctor deallocates this
       
   458     /// automatically allocated map, of course.
       
   459     /// \return <tt> (*this) </tt>
       
   460     MaxCardinalitySearch &cardinalityMap(CardinalityMap &m) {
       
   461       if(local_cardinality) {
       
   462 	delete _cardinality;
       
   463 	local_cardinality=false;
       
   464       }
       
   465       _cardinality = &m;
       
   466       return *this;
       
   467     }
       
   468 
       
   469     /// \brief Sets the map storing the processed nodes.
       
   470     ///
       
   471     /// Sets the map storing the processed nodes.
       
   472     /// If you don't use this function before calling \ref run(),
       
   473     /// it will allocate one. The destuctor deallocates this
       
   474     /// automatically allocated map, of course.
       
   475     /// \return <tt> (*this) </tt>
       
   476     MaxCardinalitySearch &processedMap(ProcessedMap &m) 
       
   477     {
       
   478       if(local_processed) {
       
   479 	delete _processed;
       
   480 	local_processed=false;
       
   481       }
       
   482       _processed = &m;
       
   483       return *this;
       
   484     }
       
   485 
       
   486     /// \brief Returns a const reference to the cardinality map.
       
   487     ///
       
   488     /// Returns a const reference to the cardinality map used by
       
   489     /// the algorithm.
       
   490     const ProcessedMap &processedMap() const {
       
   491       return *_processed;
       
   492     }
       
   493 
       
   494     /// \brief Sets the heap and the cross reference used by algorithm.
       
   495     ///
       
   496     /// Sets the heap and the cross reference used by algorithm.
       
   497     /// If you don't use this function before calling \ref run(),
       
   498     /// it will allocate one. The destuctor deallocates this
       
   499     /// automatically allocated map, of course.
       
   500     /// \return <tt> (*this) </tt>
       
   501     MaxCardinalitySearch &heap(Heap& hp, HeapCrossRef &cr) {
       
   502       if(local_heap_cross_ref) {
       
   503 	delete _heap_cross_ref;
       
   504 	local_heap_cross_ref = false;
       
   505       }
       
   506       _heap_cross_ref = &cr;
       
   507       if(local_heap) {
       
   508 	delete _heap;
       
   509 	local_heap = false;
       
   510       }
       
   511       _heap = &hp;
       
   512       return *this;
       
   513     }
       
   514 
       
   515     /// \brief Returns a const reference to the heap.
       
   516     ///
       
   517     /// Returns a const reference to the heap used by
       
   518     /// the algorithm.
       
   519     const Heap &heap() const {
       
   520       return *_heap;
       
   521     }
       
   522 
       
   523     /// \brief Returns a const reference to the cross reference.
       
   524     ///
       
   525     /// Returns a const reference to the cross reference
       
   526     /// of the heap.
       
   527     const HeapCrossRef &heapCrossRef() const {
       
   528       return *_heap_cross_ref;
       
   529     }
       
   530 
       
   531   private:
       
   532 
       
   533     typedef typename Digraph::Node Node;
       
   534     typedef typename Digraph::NodeIt NodeIt;
       
   535     typedef typename Digraph::Arc Arc;
       
   536     typedef typename Digraph::InArcIt InArcIt;
       
   537 
       
   538     void create_maps() {
       
   539       if(!_capacity) {
       
   540 	local_capacity = true;
       
   541 	_capacity = Traits::createCapacityMap(*_graph);
       
   542       }
       
   543       if(!_cardinality) {
       
   544 	local_cardinality = true;
       
   545 	_cardinality = Traits::createCardinalityMap(*_graph);
       
   546       }
       
   547       if(!_processed) {
       
   548 	local_processed = true;
       
   549 	_processed = Traits::createProcessedMap(*_graph);
       
   550       }
       
   551       if (!_heap_cross_ref) {
       
   552 	local_heap_cross_ref = true;
       
   553 	_heap_cross_ref = Traits::createHeapCrossRef(*_graph);
       
   554       }
       
   555       if (!_heap) {
       
   556 	local_heap = true;
       
   557 	_heap = Traits::createHeap(*_heap_cross_ref);
       
   558       }
       
   559     }
       
   560     
       
   561     void finalizeNodeData(Node node, Value capacity) {
       
   562       _processed->set(node, true);
       
   563       _cardinality->set(node, capacity);
       
   564     }
       
   565 
       
   566   public:
       
   567     /// \name Execution control
       
   568     /// The simplest way to execute the algorithm is to use
       
   569     /// one of the member functions called \ref run().
       
   570     /// \n
       
   571     /// If you need more control on the execution,
       
   572     /// first you must call \ref init(), then you can add several source nodes
       
   573     /// with \ref addSource().
       
   574     /// Finally \ref start() will perform the computation.
       
   575 
       
   576     ///@{
       
   577 
       
   578     /// \brief Initializes the internal data structures.
       
   579     ///
       
   580     /// Initializes the internal data structures, and clears the heap.
       
   581     void init() {
       
   582       create_maps();
       
   583       _heap->clear();
       
   584       for (NodeIt it(*_graph) ; it != INVALID ; ++it) {
       
   585 	_processed->set(it, false);
       
   586 	_heap_cross_ref->set(it, Heap::PRE_HEAP);
       
   587       }
       
   588     }
       
   589     
       
   590     /// \brief Adds a new source node.
       
   591     /// 
       
   592     /// Adds a new source node to the priority heap.
       
   593     ///
       
   594     /// It checks if the node has not yet been added to the heap.
       
   595     void addSource(Node source, Value capacity = 0) {
       
   596       if(_heap->state(source) == Heap::PRE_HEAP) {
       
   597 	_heap->push(source, capacity);
       
   598       } 
       
   599     }
       
   600     
       
   601     /// \brief Processes the next node in the priority heap
       
   602     ///
       
   603     /// Processes the next node in the priority heap.
       
   604     ///
       
   605     /// \return The processed node.
       
   606     ///
       
   607     /// \warning The priority heap must not be empty!
       
   608     Node processNextNode() {
       
   609       Node node = _heap->top(); 
       
   610       finalizeNodeData(node, _heap->prio());
       
   611       _heap->pop();
       
   612       
       
   613       for (InArcIt it(*_graph, node); it != INVALID; ++it) {
       
   614 	Node source = _graph->source(it);
       
   615 	switch (_heap->state(source)) {
       
   616 	case Heap::PRE_HEAP:
       
   617 	  _heap->push(source, (*_capacity)[it]);
       
   618 	  break;
       
   619 	case Heap::IN_HEAP:
       
   620 	  _heap->decrease(source, (*_heap)[source] + (*_capacity)[it]);
       
   621 	  break;
       
   622 	case Heap::POST_HEAP:
       
   623 	  break;
       
   624 	}
       
   625       }
       
   626       return node;
       
   627     }
       
   628 
       
   629     /// \brief Next node to be processed.
       
   630     ///
       
   631     /// Next node to be processed.
       
   632     ///
       
   633     /// \return The next node to be processed or INVALID if the 
       
   634     /// priority heap is empty.
       
   635     Node nextNode() { 
       
   636       return !_heap->empty() ? _heap->top() : INVALID;
       
   637     }
       
   638  
       
   639     /// \brief Returns \c false if there are nodes
       
   640     /// to be processed in the priority heap
       
   641     ///
       
   642     /// Returns \c false if there are nodes
       
   643     /// to be processed in the priority heap
       
   644     bool emptyQueue() { return _heap->empty(); }
       
   645     /// \brief Returns the number of the nodes to be processed 
       
   646     /// in the priority heap
       
   647     ///
       
   648     /// Returns the number of the nodes to be processed in the priority heap
       
   649     int emptySize() { return _heap->size(); }
       
   650     
       
   651     /// \brief Executes the algorithm.
       
   652     ///
       
   653     /// Executes the algorithm.
       
   654     ///
       
   655     ///\pre init() must be called and at least one node should be added
       
   656     /// with addSource() before using this function.
       
   657     ///
       
   658     /// This method runs the Maximum Cardinality Search algorithm from the 
       
   659     /// source node(s).
       
   660     void start() {
       
   661       while ( !_heap->empty() ) processNextNode();
       
   662     }
       
   663     
       
   664     /// \brief Executes the algorithm until \c dest is reached.
       
   665     ///
       
   666     /// Executes the algorithm until \c dest is reached.
       
   667     ///
       
   668     /// \pre init() must be called and at least one node should be added
       
   669     /// with addSource() before using this function.
       
   670     ///
       
   671     /// This method runs the %MaxCardinalitySearch algorithm from the source 
       
   672     /// nodes.
       
   673     void start(Node dest) {
       
   674       while ( !_heap->empty() && _heap->top()!=dest ) processNextNode();
       
   675       if ( !_heap->empty() ) finalizeNodeData(_heap->top(), _heap->prio());
       
   676     }
       
   677     
       
   678     /// \brief Executes the algorithm until a condition is met.
       
   679     ///
       
   680     /// Executes the algorithm until a condition is met.
       
   681     ///
       
   682     /// \pre init() must be called and at least one node should be added
       
   683     /// with addSource() before using this function.
       
   684     ///
       
   685     /// \param nm must be a bool (or convertible) node map. The algorithm
       
   686     /// will stop when it reaches a node \c v with <tt>nm[v]==true</tt>.
       
   687     template <typename NodeBoolMap>
       
   688     void start(const NodeBoolMap &nm) {
       
   689       while ( !_heap->empty() && !nm[_heap->top()] ) processNextNode();
       
   690       if ( !_heap->empty() ) finalizeNodeData(_heap->top(),_heap->prio());
       
   691     }
       
   692     
       
   693     /// \brief Runs the maximum cardinality search algorithm from node \c s.
       
   694     ///
       
   695     /// This method runs the %MaxCardinalitySearch algorithm from a root 
       
   696     /// node \c s.
       
   697     ///
       
   698     ///\note d.run(s) is just a shortcut of the following code.
       
   699     ///\code
       
   700     ///  d.init();
       
   701     ///  d.addSource(s);
       
   702     ///  d.start();
       
   703     ///\endcode
       
   704     void run(Node s) {
       
   705       init();
       
   706       addSource(s);
       
   707       start();
       
   708     }
       
   709 
       
   710     /// \brief Runs the maximum cardinality search algorithm for the 
       
   711     /// whole digraph.
       
   712     ///
       
   713     /// This method runs the %MaxCardinalitySearch algorithm from all 
       
   714     /// unprocessed node of the digraph.
       
   715     ///
       
   716     ///\note d.run(s) is just a shortcut of the following code.
       
   717     ///\code
       
   718     ///  d.init();
       
   719     ///  for (NodeIt it(digraph); it != INVALID; ++it) {
       
   720     ///    if (!d.reached(it)) {
       
   721     ///      d.addSource(s);
       
   722     ///      d.start();
       
   723     ///    }
       
   724     ///  }
       
   725     ///\endcode
       
   726     void run() {
       
   727       init();
       
   728       for (NodeIt it(*_graph); it != INVALID; ++it) {
       
   729         if (!reached(it)) {
       
   730           addSource(it);
       
   731           start();
       
   732         }
       
   733       }
       
   734     }
       
   735     
       
   736     ///@}
       
   737 
       
   738     /// \name Query Functions
       
   739     /// The results of the maximum cardinality search algorithm can be 
       
   740     /// obtained using these functions.
       
   741     /// \n
       
   742     /// Before the use of these functions, either run() or start() must be 
       
   743     /// called.
       
   744     
       
   745     ///@{
       
   746 
       
   747     /// \brief The cardinality of a node.
       
   748     ///
       
   749     /// Returns the cardinality of a node.
       
   750     /// \pre \ref run() must be called before using this function.
       
   751     /// \warning If node \c v in unreachable from the root the return value
       
   752     /// of this funcion is undefined.
       
   753     Value cardinality(Node node) const { return (*_cardinality)[node]; }
       
   754 
       
   755     /// \brief The current cardinality of a node.
       
   756     ///
       
   757     /// Returns the current cardinality of a node.
       
   758     /// \pre the given node should be reached but not processed
       
   759     Value currentCardinality(Node node) const { return (*_heap)[node]; }
       
   760 
       
   761     /// \brief Returns a reference to the NodeMap of cardinalities.
       
   762     ///
       
   763     /// Returns a reference to the NodeMap of cardinalities. \pre \ref run() 
       
   764     /// must be called before using this function.
       
   765     const CardinalityMap &cardinalityMap() const { return *_cardinality;}
       
   766  
       
   767     /// \brief Checks if a node is reachable from the root.
       
   768     ///
       
   769     /// Returns \c true if \c v is reachable from the root.
       
   770     /// \warning The source nodes are initated as unreached.
       
   771     /// \pre \ref run() must be called before using this function.
       
   772     bool reached(Node v) { return (*_heap_cross_ref)[v] != Heap::PRE_HEAP; }
       
   773 
       
   774     /// \brief Checks if a node is processed.
       
   775     ///
       
   776     /// Returns \c true if \c v is processed, i.e. the shortest
       
   777     /// path to \c v has already found.
       
   778     /// \pre \ref run() must be called before using this function.
       
   779     bool processed(Node v) { return (*_heap_cross_ref)[v] == Heap::POST_HEAP; }
       
   780     
       
   781     ///@}
       
   782   };
       
   783 
       
   784 }
       
   785 
       
   786 #endif