lemon/dfs.h
author hegyi
Mon, 21 Nov 2005 18:03:20 +0000
changeset 1823 cb082cdf3667
parent 1773 ea5927cef15c
child 1865 dcefd1d1377f
permissions -rw-r--r--
NewMapWin has become Dialog instead of Window. Therefore it is created dynamically, when there is need for it, instead of keeping one instance in memory. This solution is slower, but more correct than before.
alpar@906
     1
/* -*- C++ -*-
ladanyi@1435
     2
 * lemon/dfs.h - Part of LEMON, a generic C++ optimization library
alpar@906
     3
 *
alpar@1164
     4
 * Copyright (C) 2005 Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
alpar@1359
     5
 * (Egervary Research Group on Combinatorial Optimization, EGRES).
alpar@906
     6
 *
alpar@906
     7
 * Permission to use, modify and distribute this software is granted
alpar@906
     8
 * provided that this copyright notice appears in all copies. For
alpar@906
     9
 * precise terms see the accompanying LICENSE file.
alpar@906
    10
 *
alpar@906
    11
 * This software is provided "AS IS" with no warranty of any kind,
alpar@906
    12
 * express or implied, and with no claim as to its suitability for any
alpar@906
    13
 * purpose.
alpar@906
    14
 *
alpar@906
    15
 */
alpar@906
    16
alpar@921
    17
#ifndef LEMON_DFS_H
alpar@921
    18
#define LEMON_DFS_H
alpar@780
    19
alpar@780
    20
///\ingroup flowalgs
alpar@780
    21
///\file
alpar@1218
    22
///\brief Dfs algorithm.
alpar@780
    23
alpar@1218
    24
#include <lemon/list_graph.h>
klao@946
    25
#include <lemon/graph_utils.h>
alpar@921
    26
#include <lemon/invalid.h>
alpar@1218
    27
#include <lemon/error.h>
alpar@1218
    28
#include <lemon/maps.h>
alpar@780
    29
deba@1749
    30
#include <lemon/concept_check.h>
deba@1749
    31
alpar@921
    32
namespace lemon {
alpar@780
    33
alpar@1218
    34
  
alpar@1218
    35
  ///Default traits class of Dfs class.
alpar@1218
    36
alpar@1218
    37
  ///Default traits class of Dfs class.
alpar@1218
    38
  ///\param GR Graph type.
alpar@1218
    39
  template<class GR>
alpar@1218
    40
  struct DfsDefaultTraits
alpar@1218
    41
  {
alpar@1218
    42
    ///The graph type the algorithm runs on. 
alpar@1218
    43
    typedef GR Graph;
alpar@1218
    44
    ///\brief The type of the map that stores the last
alpar@1218
    45
    ///edges of the %DFS paths.
alpar@1218
    46
    /// 
alpar@1218
    47
    ///The type of the map that stores the last
alpar@1218
    48
    ///edges of the %DFS paths.
alpar@1218
    49
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@1218
    50
    ///
alpar@1218
    51
    typedef typename Graph::template NodeMap<typename GR::Edge> PredMap;
alpar@1218
    52
    ///Instantiates a PredMap.
alpar@1218
    53
 
alpar@1218
    54
    ///This function instantiates a \ref PredMap. 
alpar@1218
    55
    ///\param G is the graph, to which we would like to define the PredMap.
alpar@1218
    56
    ///\todo The graph alone may be insufficient to initialize
alpar@1218
    57
    static PredMap *createPredMap(const GR &G) 
alpar@1218
    58
    {
alpar@1218
    59
      return new PredMap(G);
alpar@1218
    60
    }
alpar@1218
    61
alpar@1218
    62
    ///The type of the map that indicates which nodes are processed.
alpar@1218
    63
 
alpar@1218
    64
    ///The type of the map that indicates which nodes are processed.
alpar@1218
    65
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@1218
    66
    ///\todo named parameter to set this type, function to read and write.
alpar@1218
    67
    typedef NullMap<typename Graph::Node,bool> ProcessedMap;
alpar@1218
    68
    ///Instantiates a ProcessedMap.
alpar@1218
    69
 
alpar@1218
    70
    ///This function instantiates a \ref ProcessedMap. 
alpar@1536
    71
    ///\param g is the graph, to which
alpar@1218
    72
    ///we would like to define the \ref ProcessedMap
alpar@1536
    73
#ifdef DOXYGEN
alpar@1536
    74
    static ProcessedMap *createProcessedMap(const GR &g)
alpar@1536
    75
#else
alpar@1367
    76
    static ProcessedMap *createProcessedMap(const GR &)
alpar@1536
    77
#endif
alpar@1218
    78
    {
alpar@1218
    79
      return new ProcessedMap();
alpar@1218
    80
    }
alpar@1218
    81
    ///The type of the map that indicates which nodes are reached.
alpar@1218
    82
 
alpar@1218
    83
    ///The type of the map that indicates which nodes are reached.
alpar@1218
    84
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@1218
    85
    ///\todo named parameter to set this type, function to read and write.
alpar@1218
    86
    typedef typename Graph::template NodeMap<bool> ReachedMap;
alpar@1218
    87
    ///Instantiates a ReachedMap.
alpar@1218
    88
 
alpar@1218
    89
    ///This function instantiates a \ref ReachedMap. 
alpar@1218
    90
    ///\param G is the graph, to which
alpar@1218
    91
    ///we would like to define the \ref ReachedMap.
alpar@1218
    92
    static ReachedMap *createReachedMap(const GR &G)
alpar@1218
    93
    {
alpar@1218
    94
      return new ReachedMap(G);
alpar@1218
    95
    }
alpar@1218
    96
    ///The type of the map that stores the dists of the nodes.
alpar@1218
    97
 
alpar@1218
    98
    ///The type of the map that stores the dists of the nodes.
alpar@1218
    99
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@1218
   100
    ///
alpar@1218
   101
    typedef typename Graph::template NodeMap<int> DistMap;
alpar@1218
   102
    ///Instantiates a DistMap.
alpar@1218
   103
 
alpar@1218
   104
    ///This function instantiates a \ref DistMap. 
alpar@1218
   105
    ///\param G is the graph, to which we would like to define the \ref DistMap
alpar@1218
   106
    static DistMap *createDistMap(const GR &G)
alpar@1218
   107
    {
alpar@1218
   108
      return new DistMap(G);
alpar@1218
   109
    }
alpar@1218
   110
  };
alpar@1218
   111
  
alpar@781
   112
  ///%DFS algorithm class.
alpar@1218
   113
  
alpar@1218
   114
  ///\ingroup flowalgs
alpar@1218
   115
  ///This class provides an efficient implementation of the %DFS algorithm.
alpar@780
   116
  ///
alpar@1218
   117
  ///\param GR The graph type the algorithm runs on. The default value is
alpar@1218
   118
  ///\ref ListGraph. The value of GR is not used directly by Dfs, it
alpar@1218
   119
  ///is only passed to \ref DfsDefaultTraits.
alpar@1218
   120
  ///\param TR Traits class to set various data types used by the algorithm.
alpar@1218
   121
  ///The default traits class is
alpar@1218
   122
  ///\ref DfsDefaultTraits "DfsDefaultTraits<GR>".
alpar@1218
   123
  ///See \ref DfsDefaultTraits for the documentation of
alpar@1218
   124
  ///a Dfs traits class.
alpar@780
   125
  ///
alpar@1218
   126
  ///\author Jacint Szabo and Alpar Juttner
alpar@780
   127
#ifdef DOXYGEN
alpar@1218
   128
  template <typename GR,
alpar@1218
   129
	    typename TR>
alpar@780
   130
#else
alpar@1218
   131
  template <typename GR=ListGraph,
alpar@1218
   132
	    typename TR=DfsDefaultTraits<GR> >
alpar@780
   133
#endif
alpar@1218
   134
  class Dfs {
alpar@780
   135
  public:
alpar@1218
   136
    /**
alpar@1218
   137
     * \brief \ref Exception for uninitialized parameters.
alpar@1218
   138
     *
alpar@1218
   139
     * This error represents problems in the initialization
alpar@1218
   140
     * of the parameters of the algorithms.
alpar@1218
   141
     */
alpar@1218
   142
    class UninitializedParameter : public lemon::UninitializedParameter {
alpar@1218
   143
    public:
alpar@1218
   144
      virtual const char* exceptionName() const {
alpar@1218
   145
	return "lemon::Dfs::UninitializedParameter";
alpar@1218
   146
      }
alpar@1218
   147
    };
alpar@1218
   148
alpar@1218
   149
    typedef TR Traits;
alpar@780
   150
    ///The type of the underlying graph.
alpar@1218
   151
    typedef typename TR::Graph Graph;
alpar@911
   152
    ///\e
alpar@780
   153
    typedef typename Graph::Node Node;
alpar@911
   154
    ///\e
alpar@780
   155
    typedef typename Graph::NodeIt NodeIt;
alpar@911
   156
    ///\e
alpar@780
   157
    typedef typename Graph::Edge Edge;
alpar@911
   158
    ///\e
alpar@780
   159
    typedef typename Graph::OutEdgeIt OutEdgeIt;
alpar@780
   160
    
alpar@780
   161
    ///\brief The type of the map that stores the last
alpar@1218
   162
    ///edges of the %DFS paths.
alpar@1218
   163
    typedef typename TR::PredMap PredMap;
alpar@1218
   164
    ///The type of the map indicating which nodes are reached.
alpar@1218
   165
    typedef typename TR::ReachedMap ReachedMap;
alpar@1218
   166
    ///The type of the map indicating which nodes are processed.
alpar@1218
   167
    typedef typename TR::ProcessedMap ProcessedMap;
alpar@1218
   168
    ///The type of the map that stores the dists of the nodes.
alpar@1218
   169
    typedef typename TR::DistMap DistMap;
alpar@780
   170
  private:
alpar@802
   171
    /// Pointer to the underlying graph.
alpar@780
   172
    const Graph *G;
alpar@802
   173
    ///Pointer to the map of predecessors edges.
alpar@1218
   174
    PredMap *_pred;
alpar@1218
   175
    ///Indicates if \ref _pred is locally allocated (\c true) or not.
alpar@1218
   176
    bool local_pred;
alpar@802
   177
    ///Pointer to the map of distances.
alpar@1218
   178
    DistMap *_dist;
alpar@1218
   179
    ///Indicates if \ref _dist is locally allocated (\c true) or not.
alpar@1218
   180
    bool local_dist;
alpar@1218
   181
    ///Pointer to the map of reached status of the nodes.
alpar@1218
   182
    ReachedMap *_reached;
alpar@1218
   183
    ///Indicates if \ref _reached is locally allocated (\c true) or not.
alpar@1218
   184
    bool local_reached;
alpar@1218
   185
    ///Pointer to the map of processed status of the nodes.
alpar@1218
   186
    ProcessedMap *_processed;
alpar@1218
   187
    ///Indicates if \ref _processed is locally allocated (\c true) or not.
alpar@1218
   188
    bool local_processed;
alpar@780
   189
alpar@1218
   190
    std::vector<typename Graph::OutEdgeIt> _stack;
alpar@1218
   191
    int _stack_head;
alpar@780
   192
alpar@1218
   193
    ///Creates the maps if necessary.
alpar@1218
   194
    
alpar@1218
   195
    ///\todo Better memory allocation (instead of new).
alpar@1218
   196
    void create_maps() 
alpar@780
   197
    {
alpar@1218
   198
      if(!_pred) {
alpar@1218
   199
	local_pred = true;
alpar@1218
   200
	_pred = Traits::createPredMap(*G);
alpar@780
   201
      }
alpar@1218
   202
      if(!_dist) {
alpar@1218
   203
	local_dist = true;
alpar@1218
   204
	_dist = Traits::createDistMap(*G);
alpar@780
   205
      }
alpar@1218
   206
      if(!_reached) {
alpar@1218
   207
	local_reached = true;
alpar@1218
   208
	_reached = Traits::createReachedMap(*G);
alpar@1218
   209
      }
alpar@1218
   210
      if(!_processed) {
alpar@1218
   211
	local_processed = true;
alpar@1218
   212
	_processed = Traits::createProcessedMap(*G);
alpar@780
   213
      }
alpar@780
   214
    }
deba@1710
   215
deba@1710
   216
  protected:
deba@1710
   217
deba@1710
   218
    Dfs() {}
alpar@780
   219
    
deba@1710
   220
  public:
deba@1709
   221
deba@1709
   222
    typedef Dfs Create;
deba@1709
   223
alpar@1218
   224
    ///\name Named template parameters
alpar@1218
   225
alpar@1218
   226
    ///@{
alpar@1218
   227
alpar@1218
   228
    template <class T>
alpar@1218
   229
    struct DefPredMapTraits : public Traits {
alpar@1218
   230
      typedef T PredMap;
alpar@1218
   231
      static PredMap *createPredMap(const Graph &G) 
alpar@1218
   232
      {
alpar@1218
   233
	throw UninitializedParameter();
alpar@1218
   234
      }
alpar@1218
   235
    };
alpar@1218
   236
    ///\ref named-templ-param "Named parameter" for setting PredMap type
alpar@1218
   237
alpar@1218
   238
    ///\ref named-templ-param "Named parameter" for setting PredMap type
alpar@1218
   239
    ///
alpar@1218
   240
    template <class T>
deba@1709
   241
    struct DefPredMap : public Dfs<Graph, DefPredMapTraits<T> > {
deba@1709
   242
      typedef Dfs<Graph, DefPredMapTraits<T> > Create;
deba@1709
   243
    };
alpar@1218
   244
    
alpar@1218
   245
    
alpar@1218
   246
    template <class T>
alpar@1218
   247
    struct DefDistMapTraits : public Traits {
alpar@1218
   248
      typedef T DistMap;
alpar@1218
   249
      static DistMap *createDistMap(const Graph &G) 
alpar@1218
   250
      {
alpar@1218
   251
	throw UninitializedParameter();
alpar@1218
   252
      }
alpar@1218
   253
    };
alpar@1218
   254
    ///\ref named-templ-param "Named parameter" for setting DistMap type
alpar@1218
   255
alpar@1218
   256
    ///\ref named-templ-param "Named parameter" for setting DistMap type
alpar@1218
   257
    ///
alpar@1218
   258
    template <class T>
deba@1709
   259
    struct DefDistMap {
deba@1709
   260
      typedef Dfs<Graph, DefDistMapTraits<T> > Create;
deba@1709
   261
    };
alpar@1218
   262
    
alpar@1218
   263
    template <class T>
alpar@1218
   264
    struct DefReachedMapTraits : public Traits {
alpar@1218
   265
      typedef T ReachedMap;
alpar@1218
   266
      static ReachedMap *createReachedMap(const Graph &G) 
alpar@1218
   267
      {
alpar@1218
   268
	throw UninitializedParameter();
alpar@1218
   269
      }
alpar@1218
   270
    };
alpar@1218
   271
    ///\ref named-templ-param "Named parameter" for setting ReachedMap type
alpar@1218
   272
alpar@1218
   273
    ///\ref named-templ-param "Named parameter" for setting ReachedMap type
alpar@1218
   274
    ///
alpar@1218
   275
    template <class T>
deba@1749
   276
    struct DefReachedMap : public Dfs< Graph, DefReachedMapTraits<T> > {
deba@1709
   277
      typedef Dfs< Graph, DefReachedMapTraits<T> > Create;
alpar@1218
   278
    };
deba@1709
   279
alpar@1218
   280
    template <class T>
alpar@1218
   281
    struct DefProcessedMapTraits : public Traits {
alpar@1218
   282
      typedef T ProcessedMap;
alpar@1218
   283
      static ProcessedMap *createProcessedMap(const Graph &G) 
alpar@1218
   284
      {
alpar@1218
   285
	throw UninitializedParameter();
alpar@1218
   286
      }
alpar@1218
   287
    };
alpar@1218
   288
    ///\ref named-templ-param "Named parameter" for setting ProcessedMap type
alpar@1218
   289
alpar@1218
   290
    ///\ref named-templ-param "Named parameter" for setting ProcessedMap type
alpar@1218
   291
    ///
alpar@1218
   292
    template <class T>
deba@1694
   293
    struct DefProcessedMap : public Dfs< Graph, DefProcessedMapTraits<T> > { 
deba@1709
   294
      typedef Dfs< Graph, DefProcessedMapTraits<T> > Create;
deba@1694
   295
    };
alpar@1218
   296
    
alpar@1218
   297
    struct DefGraphProcessedMapTraits : public Traits {
alpar@1218
   298
      typedef typename Graph::template NodeMap<bool> ProcessedMap;
alpar@1218
   299
      static ProcessedMap *createProcessedMap(const Graph &G) 
alpar@1218
   300
      {
alpar@1218
   301
	return new ProcessedMap(G);
alpar@1218
   302
      }
alpar@1218
   303
    };
alpar@1218
   304
    ///\brief \ref named-templ-param "Named parameter"
alpar@1218
   305
    ///for setting the ProcessedMap type to be Graph::NodeMap<bool>.
alpar@1218
   306
    ///
alpar@1218
   307
    ///\ref named-templ-param "Named parameter"
alpar@1218
   308
    ///for setting the ProcessedMap type to be Graph::NodeMap<bool>.
alpar@1218
   309
    ///If you don't set it explicitely, it will be automatically allocated.
alpar@1218
   310
    template <class T>
alpar@1218
   311
    class DefProcessedMapToBeDefaultMap :
deba@1709
   312
      public Dfs< Graph, DefGraphProcessedMapTraits> { 
deba@1709
   313
      typedef Dfs< Graph, DefGraphProcessedMapTraits> Create;
deba@1709
   314
    };
alpar@1218
   315
    
alpar@1218
   316
    ///@}
alpar@1218
   317
alpar@1218
   318
  public:      
alpar@1218
   319
    
alpar@802
   320
    ///Constructor.
alpar@802
   321
    
alpar@802
   322
    ///\param _G the graph the algorithm will run on.
alpar@911
   323
    ///
alpar@780
   324
    Dfs(const Graph& _G) :
alpar@780
   325
      G(&_G),
alpar@1218
   326
      _pred(NULL), local_pred(false),
alpar@1218
   327
      _dist(NULL), local_dist(false),
alpar@1218
   328
      _reached(NULL), local_reached(false),
alpar@1218
   329
      _processed(NULL), local_processed(false)
alpar@780
   330
    { }
alpar@780
   331
    
alpar@802
   332
    ///Destructor.
alpar@780
   333
    ~Dfs() 
alpar@780
   334
    {
alpar@1218
   335
      if(local_pred) delete _pred;
alpar@1218
   336
      if(local_dist) delete _dist;
alpar@1218
   337
      if(local_reached) delete _reached;
alpar@1218
   338
      if(local_processed) delete _processed;
alpar@780
   339
    }
alpar@780
   340
alpar@780
   341
    ///Sets the map storing the predecessor edges.
alpar@780
   342
alpar@780
   343
    ///Sets the map storing the predecessor edges.
alpar@780
   344
    ///If you don't use this function before calling \ref run(),
alpar@780
   345
    ///it will allocate one. The destuctor deallocates this
alpar@780
   346
    ///automatically allocated map, of course.
alpar@780
   347
    ///\return <tt> (*this) </tt>
alpar@1218
   348
    Dfs &predMap(PredMap &m) 
alpar@780
   349
    {
alpar@1218
   350
      if(local_pred) {
alpar@1218
   351
	delete _pred;
alpar@1218
   352
	local_pred=false;
alpar@780
   353
      }
alpar@1218
   354
      _pred = &m;
alpar@780
   355
      return *this;
alpar@780
   356
    }
alpar@780
   357
alpar@780
   358
    ///Sets the map storing the distances calculated by the algorithm.
alpar@780
   359
alpar@780
   360
    ///Sets the map storing the distances calculated by the algorithm.
alpar@780
   361
    ///If you don't use this function before calling \ref run(),
alpar@780
   362
    ///it will allocate one. The destuctor deallocates this
alpar@780
   363
    ///automatically allocated map, of course.
alpar@780
   364
    ///\return <tt> (*this) </tt>
alpar@1218
   365
    Dfs &distMap(DistMap &m) 
alpar@780
   366
    {
alpar@1218
   367
      if(local_dist) {
alpar@1218
   368
	delete _dist;
alpar@1218
   369
	local_dist=false;
alpar@780
   370
      }
alpar@1218
   371
      _dist = &m;
alpar@780
   372
      return *this;
alpar@780
   373
    }
alpar@780
   374
alpar@1220
   375
    ///Sets the map indicating if a node is reached.
alpar@1220
   376
alpar@1220
   377
    ///Sets the map indicating if a node is reached.
alpar@1220
   378
    ///If you don't use this function before calling \ref run(),
alpar@1220
   379
    ///it will allocate one. The destuctor deallocates this
alpar@1220
   380
    ///automatically allocated map, of course.
alpar@1220
   381
    ///\return <tt> (*this) </tt>
alpar@1220
   382
    Dfs &reachedMap(ReachedMap &m) 
alpar@1220
   383
    {
alpar@1220
   384
      if(local_reached) {
alpar@1220
   385
	delete _reached;
alpar@1220
   386
	local_reached=false;
alpar@1220
   387
      }
alpar@1220
   388
      _reached = &m;
alpar@1220
   389
      return *this;
alpar@1220
   390
    }
alpar@1220
   391
alpar@1220
   392
    ///Sets the map indicating if a node is processed.
alpar@1220
   393
alpar@1220
   394
    ///Sets the map indicating if a node is processed.
alpar@1220
   395
    ///If you don't use this function before calling \ref run(),
alpar@1220
   396
    ///it will allocate one. The destuctor deallocates this
alpar@1220
   397
    ///automatically allocated map, of course.
alpar@1220
   398
    ///\return <tt> (*this) </tt>
alpar@1220
   399
    Dfs &processedMap(ProcessedMap &m) 
alpar@1220
   400
    {
alpar@1220
   401
      if(local_processed) {
alpar@1220
   402
	delete _processed;
alpar@1220
   403
	local_processed=false;
alpar@1220
   404
      }
alpar@1220
   405
      _processed = &m;
alpar@1220
   406
      return *this;
alpar@1220
   407
    }
alpar@1220
   408
alpar@1218
   409
  public:
alpar@1218
   410
    ///\name Execution control
alpar@1218
   411
    ///The simplest way to execute the algorithm is to use
alpar@1218
   412
    ///one of the member functions called \c run(...).
alpar@1218
   413
    ///\n
alpar@1218
   414
    ///If you need more control on the execution,
deba@1761
   415
    ///first you must call \ref init(), then you can add a source node
alpar@1218
   416
    ///with \ref addSource().
alpar@1218
   417
    ///Finally \ref start() will perform the actual path
alpar@1218
   418
    ///computation.
alpar@1218
   419
alpar@1218
   420
    ///@{
alpar@1218
   421
alpar@1218
   422
    ///Initializes the internal data structures.
alpar@1218
   423
alpar@1218
   424
    ///Initializes the internal data structures.
alpar@1218
   425
    ///
alpar@1218
   426
    void init()
alpar@1218
   427
    {
alpar@1218
   428
      create_maps();
alpar@1218
   429
      _stack.resize(countNodes(*G));
alpar@1218
   430
      _stack_head=-1;
alpar@780
   431
      for ( NodeIt u(*G) ; u!=INVALID ; ++u ) {
alpar@1218
   432
	_pred->set(u,INVALID);
alpar@1218
   433
	// _predNode->set(u,INVALID);
alpar@1218
   434
	_reached->set(u,false);
alpar@1218
   435
	_processed->set(u,false);
alpar@780
   436
      }
alpar@780
   437
    }
alpar@780
   438
    
alpar@1218
   439
    ///Adds a new source node.
alpar@780
   440
alpar@1218
   441
    ///Adds a new source node to the set of nodes to be processed.
alpar@1218
   442
    ///
athos@1443
   443
    ///\bug dists are wrong (or at least strange) in case of multiple sources.
alpar@1218
   444
    void addSource(Node s)
alpar@1218
   445
    {
alpar@1218
   446
      if(!(*_reached)[s])
alpar@1218
   447
	{
alpar@1218
   448
	  _reached->set(s,true);
alpar@1218
   449
	  _pred->set(s,INVALID);
alpar@1664
   450
	  OutEdgeIt e(*G,s);
alpar@1666
   451
	  if(e!=INVALID) {
alpar@1666
   452
	    _stack[++_stack_head]=e;
alpar@1666
   453
	    _dist->set(s,_stack_head);
alpar@1666
   454
	  }
alpar@1666
   455
	  else {
alpar@1666
   456
	    _processed->set(s,true);
alpar@1666
   457
	    _dist->set(s,0);
alpar@1666
   458
	  }
alpar@1218
   459
	}
alpar@1218
   460
    }
alpar@1218
   461
    
deba@1529
   462
    ///Processes the next edge.
alpar@1218
   463
deba@1529
   464
    ///Processes the next edge.
alpar@1218
   465
    ///
alpar@1516
   466
    ///\return The processed edge.
alpar@1516
   467
    ///
athos@1443
   468
    ///\pre The stack must not be empty!
alpar@1516
   469
    Edge processNextEdge()
alpar@1218
   470
    { 
alpar@1218
   471
      Node m;
alpar@1218
   472
      Edge e=_stack[_stack_head];
alpar@1218
   473
      if(!(*_reached)[m=G->target(e)]) {
alpar@1218
   474
	_pred->set(m,e);
alpar@1218
   475
	_reached->set(m,true);
alpar@1233
   476
	++_stack_head;
alpar@1233
   477
	_stack[_stack_head] = OutEdgeIt(*G, m);
alpar@1218
   478
	_dist->set(m,_stack_head);
alpar@1218
   479
      }
alpar@1218
   480
      else {
alpar@1663
   481
	m=G->source(e);
alpar@1663
   482
	++_stack[_stack_head];
alpar@1663
   483
      }
alpar@1663
   484
      while(_stack_head>=0 && _stack[_stack_head]==INVALID) {
alpar@1663
   485
	_processed->set(m,true);
alpar@1663
   486
	--_stack_head;
alpar@1663
   487
	if(_stack_head>=0) {
alpar@1663
   488
	  m=G->source(_stack[_stack_head]);
alpar@1663
   489
	  ++_stack[_stack_head];
alpar@1663
   490
	}
alpar@1218
   491
      }
alpar@1516
   492
      return e;
alpar@1218
   493
    }
alpar@1665
   494
    ///Next edge to be processed.
alpar@1665
   495
alpar@1665
   496
    ///Next edge to be processed.
alpar@1665
   497
    ///
alpar@1665
   498
    ///\return The next edge to be processed or INVALID if the stack is
alpar@1665
   499
    /// empty.
deba@1694
   500
    OutEdgeIt nextEdge()
alpar@1665
   501
    { 
alpar@1665
   502
      return _stack_head>=0?_stack[_stack_head]:INVALID;
alpar@1665
   503
    }
deba@1694
   504
alpar@1218
   505
    ///\brief Returns \c false if there are nodes
alpar@1218
   506
    ///to be processed in the queue
alpar@1218
   507
    ///
alpar@1218
   508
    ///Returns \c false if there are nodes
alpar@1218
   509
    ///to be processed in the queue
alpar@1218
   510
    bool emptyQueue() { return _stack_head<0; }
alpar@1218
   511
    ///Returns the number of the nodes to be processed.
alpar@1218
   512
    
alpar@1218
   513
    ///Returns the number of the nodes to be processed in the queue.
alpar@1218
   514
    int queueSize() { return _stack_head+1; }
alpar@1218
   515
    
alpar@1218
   516
    ///Executes the algorithm.
alpar@1218
   517
alpar@1218
   518
    ///Executes the algorithm.
alpar@1218
   519
    ///
alpar@1218
   520
    ///\pre init() must be called and at least one node should be added
alpar@1218
   521
    ///with addSource() before using this function.
alpar@1218
   522
    ///
alpar@1218
   523
    ///This method runs the %DFS algorithm from the root node(s)
alpar@1218
   524
    ///in order to
alpar@1218
   525
    ///compute the
alpar@1218
   526
    ///%DFS path to each node. The algorithm computes
alpar@1218
   527
    ///- The %DFS tree.
athos@1443
   528
    ///- The distance of each node from the root(s) in the %DFS tree.
alpar@1218
   529
    ///
alpar@1218
   530
    void start()
alpar@1218
   531
    {
alpar@1218
   532
      while ( !emptyQueue() ) processNextEdge();
alpar@1218
   533
    }
alpar@1218
   534
    
alpar@1218
   535
    ///Executes the algorithm until \c dest is reached.
alpar@1218
   536
alpar@1218
   537
    ///Executes the algorithm until \c dest is reached.
alpar@1218
   538
    ///
alpar@1218
   539
    ///\pre init() must be called and at least one node should be added
alpar@1218
   540
    ///with addSource() before using this function.
alpar@1218
   541
    ///
alpar@1218
   542
    ///This method runs the %DFS algorithm from the root node(s)
alpar@1218
   543
    ///in order to
alpar@1218
   544
    ///compute the
alpar@1218
   545
    ///%DFS path to \c dest. The algorithm computes
alpar@1218
   546
    ///- The %DFS path to \c  dest.
athos@1443
   547
    ///- The distance of \c dest from the root(s) in the %DFS tree.
alpar@1218
   548
    ///
alpar@1218
   549
    void start(Node dest)
alpar@1218
   550
    {
alpar@1233
   551
      while ( !emptyQueue() && G->target(_stack[_stack_head])!=dest ) 
alpar@1233
   552
	processNextEdge();
alpar@1218
   553
    }
alpar@1218
   554
    
alpar@1218
   555
    ///Executes the algorithm until a condition is met.
alpar@1218
   556
alpar@1218
   557
    ///Executes the algorithm until a condition is met.
alpar@1218
   558
    ///
alpar@1218
   559
    ///\pre init() must be called and at least one node should be added
alpar@1218
   560
    ///with addSource() before using this function.
alpar@1218
   561
    ///
alpar@1233
   562
    ///\param nm must be a bool (or convertible) edge map. The algorithm
athos@1438
   563
    ///will stop when it reaches an edge \c e with <tt>nm[e]==true</tt>.
athos@1443
   564
    ///
deba@1749
   565
    ///\warning Contrary to \ref Dfs and \ref Dijkstra, \c em is an edge map,
alpar@1233
   566
    ///not a node map.
deba@1749
   567
    template<class EM>
deba@1749
   568
    void start(const EM &em)
deba@1749
   569
    {
deba@1749
   570
      while ( !emptyQueue() && !em[_stack[_stack_head]] ) processNextEdge();
deba@1749
   571
    }
deba@1749
   572
alpar@1218
   573
    ///Runs %DFS algorithm from node \c s.
alpar@1218
   574
    
alpar@1218
   575
    ///This method runs the %DFS algorithm from a root node \c s
alpar@1218
   576
    ///in order to
alpar@1218
   577
    ///compute the
alpar@1218
   578
    ///%DFS path to each node. The algorithm computes
alpar@1218
   579
    ///- The %DFS tree.
athos@1443
   580
    ///- The distance of each node from the root in the %DFS tree.
alpar@1218
   581
    ///
alpar@1218
   582
    ///\note d.run(s) is just a shortcut of the following code.
alpar@1218
   583
    ///\code
alpar@1218
   584
    ///  d.init();
alpar@1218
   585
    ///  d.addSource(s);
alpar@1218
   586
    ///  d.start();
alpar@1218
   587
    ///\endcode
alpar@1218
   588
    void run(Node s) {
alpar@1218
   589
      init();
alpar@1218
   590
      addSource(s);
alpar@1218
   591
      start();
alpar@1218
   592
    }
alpar@1218
   593
    
alpar@1218
   594
    ///Finds the %DFS path between \c s and \c t.
alpar@1218
   595
    
alpar@1218
   596
    ///Finds the %DFS path between \c s and \c t.
alpar@1218
   597
    ///
alpar@1218
   598
    ///\return The length of the %DFS s---t path if there exists one,
alpar@1218
   599
    ///0 otherwise.
athos@1540
   600
    ///\note Apart from the return value, d.run(s,t) is
alpar@1218
   601
    ///just a shortcut of the following code.
alpar@1218
   602
    ///\code
alpar@1218
   603
    ///  d.init();
alpar@1218
   604
    ///  d.addSource(s);
alpar@1218
   605
    ///  d.start(t);
alpar@1218
   606
    ///\endcode
alpar@1218
   607
    int run(Node s,Node t) {
alpar@1218
   608
      init();
alpar@1218
   609
      addSource(s);
alpar@1218
   610
      start(t);
alpar@1233
   611
      return reached(t)?_stack_head+1:0;
alpar@1218
   612
    }
alpar@1218
   613
    
alpar@1218
   614
    ///@}
alpar@1218
   615
alpar@1218
   616
    ///\name Query Functions
alpar@1218
   617
    ///The result of the %DFS algorithm can be obtained using these
alpar@1218
   618
    ///functions.\n
alpar@1218
   619
    ///Before the use of these functions,
alpar@1218
   620
    ///either run() or start() must be called.
alpar@1218
   621
    
alpar@1218
   622
    ///@{
alpar@1218
   623
alpar@1283
   624
    ///Copies the path to \c t on the DFS tree into \c p
alpar@1283
   625
    
athos@1443
   626
    ///This function copies the path to \c t on the DFS tree  into \c p.
athos@1438
   627
    ///If \c t is a source itself or unreachable, then it does not
alpar@1283
   628
    ///alter \c p.
athos@1438
   629
    ///
alpar@1283
   630
    ///\return Returns \c true if a path to \c t was actually copied to \c p,
alpar@1283
   631
    ///\c false otherwise.
alpar@1283
   632
    ///\sa DirPath
alpar@1283
   633
    template<class P>
alpar@1283
   634
    bool getPath(P &p,Node t) 
alpar@1283
   635
    {
alpar@1283
   636
      if(reached(t)) {
alpar@1283
   637
	p.clear();
alpar@1283
   638
	typename P::Builder b(p);
deba@1763
   639
	for(b.setStartNode(t);predEdge(t)!=INVALID;t=predNode(t))
deba@1763
   640
	  b.pushFront(predEdge(t));
alpar@1283
   641
	b.commit();
alpar@1283
   642
	return true;
alpar@1283
   643
      }
alpar@1283
   644
      return false;
alpar@1283
   645
    }
alpar@1283
   646
alpar@1218
   647
    ///The distance of a node from the root(s).
alpar@1218
   648
alpar@1218
   649
    ///Returns the distance of a node from the root(s).
alpar@780
   650
    ///\pre \ref run() must be called before using this function.
athos@1438
   651
    ///\warning If node \c v is unreachable from the root(s) then the return value
alpar@780
   652
    ///of this funcion is undefined.
alpar@1218
   653
    int dist(Node v) const { return (*_dist)[v]; }
alpar@780
   654
alpar@1218
   655
    ///Returns the 'previous edge' of the %DFS tree.
alpar@780
   656
alpar@1218
   657
    ///For a node \c v it returns the 'previous edge'
alpar@1218
   658
    ///of the %DFS path,
alpar@1218
   659
    ///i.e. it returns the last edge of a %DFS path from the root(s) to \c
alpar@780
   660
    ///v. It is \ref INVALID
alpar@1218
   661
    ///if \c v is unreachable from the root(s) or \c v is a root. The
alpar@781
   662
    ///%DFS tree used here is equal to the %DFS tree used in
alpar@1631
   663
    ///\ref predNode().
alpar@1218
   664
    ///\pre Either \ref run() or \ref start() must be called before using
alpar@780
   665
    ///this function.
deba@1763
   666
    Edge predEdge(Node v) const { return (*_pred)[v];}
alpar@780
   667
alpar@781
   668
    ///Returns the 'previous node' of the %DFS tree.
alpar@780
   669
alpar@1218
   670
    ///For a node \c v it returns the 'previous node'
alpar@1218
   671
    ///of the %DFS tree,
alpar@1218
   672
    ///i.e. it returns the last but one node from a %DFS path from the
alpar@1218
   673
    ///root(a) to \c /v.
alpar@1218
   674
    ///It is INVALID if \c v is unreachable from the root(s) or
alpar@1218
   675
    ///if \c v itself a root.
alpar@1218
   676
    ///The %DFS tree used here is equal to the %DFS
deba@1763
   677
    ///tree used in \ref predEdge().
alpar@1218
   678
    ///\pre Either \ref run() or \ref start() must be called before
alpar@780
   679
    ///using this function.
alpar@1218
   680
    Node predNode(Node v) const { return (*_pred)[v]==INVALID ? INVALID:
alpar@1218
   681
				  G->source((*_pred)[v]); }
alpar@780
   682
    
alpar@1218
   683
    ///Returns a reference to the NodeMap of distances.
alpar@1218
   684
alpar@1218
   685
    ///Returns a reference to the NodeMap of distances.
alpar@1218
   686
    ///\pre Either \ref run() or \ref init() must
alpar@780
   687
    ///be called before using this function.
alpar@1218
   688
    const DistMap &distMap() const { return *_dist;}
alpar@780
   689
 
alpar@1218
   690
    ///Returns a reference to the %DFS edge-tree map.
alpar@780
   691
alpar@780
   692
    ///Returns a reference to the NodeMap of the edges of the
alpar@781
   693
    ///%DFS tree.
alpar@1218
   694
    ///\pre Either \ref run() or \ref init()
alpar@1218
   695
    ///must be called before using this function.
alpar@1218
   696
    const PredMap &predMap() const { return *_pred;}
alpar@780
   697
 
alpar@780
   698
    ///Checks if a node is reachable from the root.
alpar@780
   699
athos@1438
   700
    ///Returns \c true if \c v is reachable from the root(s).
athos@1438
   701
    ///\warning The source nodes are inditated as unreachable.
alpar@1218
   702
    ///\pre Either \ref run() or \ref start()
alpar@1218
   703
    ///must be called before using this function.
alpar@780
   704
    ///
alpar@1218
   705
    bool reached(Node v) { return (*_reached)[v]; }
alpar@1218
   706
    
alpar@1218
   707
    ///@}
alpar@1218
   708
  };
alpar@1218
   709
alpar@1218
   710
  ///Default traits class of Dfs function.
alpar@1218
   711
alpar@1218
   712
  ///Default traits class of Dfs function.
alpar@1218
   713
  ///\param GR Graph type.
alpar@1218
   714
  template<class GR>
alpar@1218
   715
  struct DfsWizardDefaultTraits
alpar@1218
   716
  {
alpar@1218
   717
    ///The graph type the algorithm runs on. 
alpar@1218
   718
    typedef GR Graph;
alpar@1218
   719
    ///\brief The type of the map that stores the last
alpar@1218
   720
    ///edges of the %DFS paths.
alpar@1218
   721
    /// 
alpar@1218
   722
    ///The type of the map that stores the last
alpar@1218
   723
    ///edges of the %DFS paths.
alpar@1218
   724
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@780
   725
    ///
alpar@1218
   726
    typedef NullMap<typename Graph::Node,typename GR::Edge> PredMap;
alpar@1218
   727
    ///Instantiates a PredMap.
alpar@1218
   728
 
alpar@1218
   729
    ///This function instantiates a \ref PredMap. 
alpar@1536
   730
    ///\param g is the graph, to which we would like to define the PredMap.
alpar@1218
   731
    ///\todo The graph alone may be insufficient to initialize
alpar@1536
   732
#ifdef DOXYGEN
alpar@1536
   733
    static PredMap *createPredMap(const GR &g) 
alpar@1536
   734
#else
alpar@1367
   735
    static PredMap *createPredMap(const GR &) 
alpar@1536
   736
#endif
alpar@1218
   737
    {
alpar@1218
   738
      return new PredMap();
alpar@1218
   739
    }
alpar@1218
   740
alpar@1218
   741
    ///The type of the map that indicates which nodes are processed.
alpar@1218
   742
 
alpar@1218
   743
    ///The type of the map that indicates which nodes are processed.
alpar@1218
   744
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@1218
   745
    ///\todo named parameter to set this type, function to read and write.
alpar@1218
   746
    typedef NullMap<typename Graph::Node,bool> ProcessedMap;
alpar@1218
   747
    ///Instantiates a ProcessedMap.
alpar@1218
   748
 
alpar@1218
   749
    ///This function instantiates a \ref ProcessedMap. 
alpar@1536
   750
    ///\param g is the graph, to which
alpar@1218
   751
    ///we would like to define the \ref ProcessedMap
alpar@1536
   752
#ifdef DOXYGEN
alpar@1536
   753
    static ProcessedMap *createProcessedMap(const GR &g)
alpar@1536
   754
#else
alpar@1367
   755
    static ProcessedMap *createProcessedMap(const GR &)
alpar@1536
   756
#endif
alpar@1218
   757
    {
alpar@1218
   758
      return new ProcessedMap();
alpar@1218
   759
    }
alpar@1218
   760
    ///The type of the map that indicates which nodes are reached.
alpar@1218
   761
 
alpar@1218
   762
    ///The type of the map that indicates which nodes are reached.
alpar@1218
   763
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@1218
   764
    ///\todo named parameter to set this type, function to read and write.
alpar@1218
   765
    typedef typename Graph::template NodeMap<bool> ReachedMap;
alpar@1218
   766
    ///Instantiates a ReachedMap.
alpar@1218
   767
 
alpar@1218
   768
    ///This function instantiates a \ref ReachedMap. 
alpar@1218
   769
    ///\param G is the graph, to which
alpar@1218
   770
    ///we would like to define the \ref ReachedMap.
alpar@1218
   771
    static ReachedMap *createReachedMap(const GR &G)
alpar@1218
   772
    {
alpar@1218
   773
      return new ReachedMap(G);
alpar@1218
   774
    }
alpar@1218
   775
    ///The type of the map that stores the dists of the nodes.
alpar@1218
   776
 
alpar@1218
   777
    ///The type of the map that stores the dists of the nodes.
alpar@1218
   778
    ///It must meet the \ref concept::WriteMap "WriteMap" concept.
alpar@1218
   779
    ///
alpar@1218
   780
    typedef NullMap<typename Graph::Node,int> DistMap;
alpar@1218
   781
    ///Instantiates a DistMap.
alpar@1218
   782
 
alpar@1218
   783
    ///This function instantiates a \ref DistMap. 
alpar@1536
   784
    ///\param g is the graph, to which we would like to define the \ref DistMap
alpar@1536
   785
#ifdef DOXYGEN
alpar@1536
   786
    static DistMap *createDistMap(const GR &g)
alpar@1536
   787
#else
alpar@1367
   788
    static DistMap *createDistMap(const GR &)
alpar@1536
   789
#endif
alpar@1218
   790
    {
alpar@1218
   791
      return new DistMap();
alpar@1218
   792
    }
alpar@1218
   793
  };
alpar@1218
   794
  
alpar@1218
   795
  /// Default traits used by \ref DfsWizard
alpar@1218
   796
alpar@1218
   797
  /// To make it easier to use Dfs algorithm
alpar@1218
   798
  ///we have created a wizard class.
alpar@1218
   799
  /// This \ref DfsWizard class needs default traits,
alpar@1218
   800
  ///as well as the \ref Dfs class.
alpar@1218
   801
  /// The \ref DfsWizardBase is a class to be the default traits of the
alpar@1218
   802
  /// \ref DfsWizard class.
alpar@1218
   803
  template<class GR>
alpar@1218
   804
  class DfsWizardBase : public DfsWizardDefaultTraits<GR>
alpar@1218
   805
  {
alpar@1218
   806
alpar@1218
   807
    typedef DfsWizardDefaultTraits<GR> Base;
alpar@1218
   808
  protected:
alpar@1218
   809
    /// Type of the nodes in the graph.
alpar@1218
   810
    typedef typename Base::Graph::Node Node;
alpar@1218
   811
alpar@1218
   812
    /// Pointer to the underlying graph.
alpar@1218
   813
    void *_g;
alpar@1218
   814
    ///Pointer to the map of reached nodes.
alpar@1218
   815
    void *_reached;
alpar@1218
   816
    ///Pointer to the map of processed nodes.
alpar@1218
   817
    void *_processed;
alpar@1218
   818
    ///Pointer to the map of predecessors edges.
alpar@1218
   819
    void *_pred;
alpar@1218
   820
    ///Pointer to the map of distances.
alpar@1218
   821
    void *_dist;
alpar@1218
   822
    ///Pointer to the source node.
alpar@1218
   823
    Node _source;
alpar@1218
   824
    
alpar@1218
   825
    public:
alpar@1218
   826
    /// Constructor.
alpar@1218
   827
    
alpar@1218
   828
    /// This constructor does not require parameters, therefore it initiates
alpar@1218
   829
    /// all of the attributes to default values (0, INVALID).
alpar@1218
   830
    DfsWizardBase() : _g(0), _reached(0), _processed(0), _pred(0),
alpar@1218
   831
			   _dist(0), _source(INVALID) {}
alpar@1218
   832
alpar@1218
   833
    /// Constructor.
alpar@1218
   834
    
alpar@1218
   835
    /// This constructor requires some parameters,
alpar@1218
   836
    /// listed in the parameters list.
alpar@1218
   837
    /// Others are initiated to 0.
alpar@1218
   838
    /// \param g is the initial value of  \ref _g
alpar@1218
   839
    /// \param s is the initial value of  \ref _source
alpar@1218
   840
    DfsWizardBase(const GR &g, Node s=INVALID) :
alpar@1218
   841
      _g((void *)&g), _reached(0), _processed(0), _pred(0),
alpar@1218
   842
      _dist(0), _source(s) {}
alpar@1218
   843
alpar@1218
   844
  };
alpar@1218
   845
  
athos@1443
   846
  /// A class to make the usage of the Dfs algorithm easier
alpar@1218
   847
athos@1443
   848
  /// This class is created to make it easier to use the Dfs algorithm.
alpar@1218
   849
  /// It uses the functions and features of the plain \ref Dfs,
alpar@1218
   850
  /// but it is much simpler to use it.
alpar@1218
   851
  ///
alpar@1218
   852
  /// Simplicity means that the way to change the types defined
alpar@1218
   853
  /// in the traits class is based on functions that returns the new class
alpar@1218
   854
  /// and not on templatable built-in classes.
alpar@1218
   855
  /// When using the plain \ref Dfs
alpar@1218
   856
  /// the new class with the modified type comes from
alpar@1218
   857
  /// the original class by using the ::
alpar@1218
   858
  /// operator. In the case of \ref DfsWizard only
alpar@1218
   859
  /// a function have to be called and it will
alpar@1218
   860
  /// return the needed class.
alpar@1218
   861
  ///
alpar@1218
   862
  /// It does not have own \ref run method. When its \ref run method is called
athos@1438
   863
  /// it initiates a plain \ref Dfs object, and calls the \ref Dfs::run
alpar@1218
   864
  /// method of it.
alpar@1218
   865
  template<class TR>
alpar@1218
   866
  class DfsWizard : public TR
alpar@1218
   867
  {
alpar@1218
   868
    typedef TR Base;
alpar@1218
   869
alpar@1218
   870
    ///The type of the underlying graph.
alpar@1218
   871
    typedef typename TR::Graph Graph;
alpar@1218
   872
    //\e
alpar@1218
   873
    typedef typename Graph::Node Node;
alpar@1218
   874
    //\e
alpar@1218
   875
    typedef typename Graph::NodeIt NodeIt;
alpar@1218
   876
    //\e
alpar@1218
   877
    typedef typename Graph::Edge Edge;
alpar@1218
   878
    //\e
alpar@1218
   879
    typedef typename Graph::OutEdgeIt OutEdgeIt;
alpar@1218
   880
    
alpar@1218
   881
    ///\brief The type of the map that stores
alpar@1218
   882
    ///the reached nodes
alpar@1218
   883
    typedef typename TR::ReachedMap ReachedMap;
alpar@1218
   884
    ///\brief The type of the map that stores
alpar@1218
   885
    ///the processed nodes
alpar@1218
   886
    typedef typename TR::ProcessedMap ProcessedMap;
alpar@1218
   887
    ///\brief The type of the map that stores the last
alpar@1218
   888
    ///edges of the %DFS paths.
alpar@1218
   889
    typedef typename TR::PredMap PredMap;
athos@1443
   890
    ///The type of the map that stores the distances of the nodes.
alpar@1218
   891
    typedef typename TR::DistMap DistMap;
alpar@1218
   892
alpar@1218
   893
public:
alpar@1218
   894
    /// Constructor.
alpar@1218
   895
    DfsWizard() : TR() {}
alpar@1218
   896
alpar@1218
   897
    /// Constructor that requires parameters.
alpar@1218
   898
alpar@1218
   899
    /// Constructor that requires parameters.
alpar@1218
   900
    /// These parameters will be the default values for the traits class.
alpar@1218
   901
    DfsWizard(const Graph &g, Node s=INVALID) :
alpar@1218
   902
      TR(g,s) {}
alpar@1218
   903
alpar@1218
   904
    ///Copy constructor
alpar@1218
   905
    DfsWizard(const TR &b) : TR(b) {}
alpar@1218
   906
alpar@1218
   907
    ~DfsWizard() {}
alpar@1218
   908
alpar@1218
   909
    ///Runs Dfs algorithm from a given node.
alpar@1218
   910
    
alpar@1218
   911
    ///Runs Dfs algorithm from a given node.
alpar@1218
   912
    ///The node can be given by the \ref source function.
alpar@1218
   913
    void run()
alpar@1218
   914
    {
alpar@1218
   915
      if(Base::_source==INVALID) throw UninitializedParameter();
alpar@1218
   916
      Dfs<Graph,TR> alg(*(Graph*)Base::_g);
alpar@1218
   917
      if(Base::_reached) alg.reachedMap(*(ReachedMap*)Base::_reached);
alpar@1218
   918
      if(Base::_processed) alg.processedMap(*(ProcessedMap*)Base::_processed);
alpar@1218
   919
      if(Base::_pred) alg.predMap(*(PredMap*)Base::_pred);
alpar@1218
   920
      if(Base::_dist) alg.distMap(*(DistMap*)Base::_dist);
alpar@1218
   921
      alg.run(Base::_source);
alpar@1218
   922
    }
alpar@1218
   923
alpar@1218
   924
    ///Runs Dfs algorithm from the given node.
alpar@1218
   925
alpar@1218
   926
    ///Runs Dfs algorithm from the given node.
alpar@1218
   927
    ///\param s is the given source.
alpar@1218
   928
    void run(Node s)
alpar@1218
   929
    {
alpar@1218
   930
      Base::_source=s;
alpar@1218
   931
      run();
alpar@1218
   932
    }
alpar@1218
   933
alpar@1218
   934
    template<class T>
alpar@1218
   935
    struct DefPredMapBase : public Base {
alpar@1218
   936
      typedef T PredMap;
alpar@1367
   937
      static PredMap *createPredMap(const Graph &) { return 0; };
alpar@1236
   938
      DefPredMapBase(const TR &b) : TR(b) {}
alpar@1218
   939
    };
alpar@1218
   940
    
alpar@1218
   941
    ///\brief \ref named-templ-param "Named parameter"
alpar@1218
   942
    ///function for setting PredMap type
alpar@1218
   943
    ///
alpar@1218
   944
    /// \ref named-templ-param "Named parameter"
alpar@1218
   945
    ///function for setting PredMap type
alpar@1218
   946
    ///
alpar@1218
   947
    template<class T>
alpar@1218
   948
    DfsWizard<DefPredMapBase<T> > predMap(const T &t) 
alpar@1218
   949
    {
alpar@1218
   950
      Base::_pred=(void *)&t;
alpar@1218
   951
      return DfsWizard<DefPredMapBase<T> >(*this);
alpar@1218
   952
    }
alpar@1218
   953
    
alpar@1218
   954
 
alpar@1218
   955
    template<class T>
alpar@1218
   956
    struct DefReachedMapBase : public Base {
alpar@1218
   957
      typedef T ReachedMap;
alpar@1367
   958
      static ReachedMap *createReachedMap(const Graph &) { return 0; };
alpar@1236
   959
      DefReachedMapBase(const TR &b) : TR(b) {}
alpar@1218
   960
    };
alpar@1218
   961
    
alpar@1218
   962
    ///\brief \ref named-templ-param "Named parameter"
alpar@1218
   963
    ///function for setting ReachedMap
alpar@1218
   964
    ///
alpar@1218
   965
    /// \ref named-templ-param "Named parameter"
alpar@1218
   966
    ///function for setting ReachedMap
alpar@1218
   967
    ///
alpar@1218
   968
    template<class T>
alpar@1218
   969
    DfsWizard<DefReachedMapBase<T> > reachedMap(const T &t) 
alpar@1218
   970
    {
alpar@1218
   971
      Base::_pred=(void *)&t;
alpar@1218
   972
      return DfsWizard<DefReachedMapBase<T> >(*this);
alpar@1218
   973
    }
alpar@1218
   974
    
alpar@1218
   975
alpar@1218
   976
    template<class T>
alpar@1218
   977
    struct DefProcessedMapBase : public Base {
alpar@1218
   978
      typedef T ProcessedMap;
alpar@1367
   979
      static ProcessedMap *createProcessedMap(const Graph &) { return 0; };
alpar@1236
   980
      DefProcessedMapBase(const TR &b) : TR(b) {}
alpar@1218
   981
    };
alpar@1218
   982
    
alpar@1218
   983
    ///\brief \ref named-templ-param "Named parameter"
alpar@1218
   984
    ///function for setting ProcessedMap
alpar@1218
   985
    ///
alpar@1218
   986
    /// \ref named-templ-param "Named parameter"
alpar@1218
   987
    ///function for setting ProcessedMap
alpar@1218
   988
    ///
alpar@1218
   989
    template<class T>
alpar@1218
   990
    DfsWizard<DefProcessedMapBase<T> > processedMap(const T &t) 
alpar@1218
   991
    {
alpar@1218
   992
      Base::_pred=(void *)&t;
alpar@1218
   993
      return DfsWizard<DefProcessedMapBase<T> >(*this);
alpar@1218
   994
    }
alpar@1218
   995
    
alpar@1218
   996
    template<class T>
alpar@1218
   997
    struct DefDistMapBase : public Base {
alpar@1218
   998
      typedef T DistMap;
alpar@1367
   999
      static DistMap *createDistMap(const Graph &) { return 0; };
alpar@1236
  1000
      DefDistMapBase(const TR &b) : TR(b) {}
alpar@1218
  1001
    };
alpar@1218
  1002
    
alpar@1218
  1003
    ///\brief \ref named-templ-param "Named parameter"
alpar@1218
  1004
    ///function for setting DistMap type
alpar@1218
  1005
    ///
alpar@1218
  1006
    /// \ref named-templ-param "Named parameter"
alpar@1218
  1007
    ///function for setting DistMap type
alpar@1218
  1008
    ///
alpar@1218
  1009
    template<class T>
alpar@1218
  1010
    DfsWizard<DefDistMapBase<T> > distMap(const T &t) 
alpar@1218
  1011
    {
alpar@1218
  1012
      Base::_dist=(void *)&t;
alpar@1218
  1013
      return DfsWizard<DefDistMapBase<T> >(*this);
alpar@1218
  1014
    }
alpar@1218
  1015
    
alpar@1218
  1016
    /// Sets the source node, from which the Dfs algorithm runs.
alpar@1218
  1017
alpar@1218
  1018
    /// Sets the source node, from which the Dfs algorithm runs.
alpar@1218
  1019
    /// \param s is the source node.
alpar@1218
  1020
    DfsWizard<TR> &source(Node s) 
alpar@1218
  1021
    {
alpar@1218
  1022
      Base::_source=s;
alpar@1218
  1023
      return *this;
alpar@1218
  1024
    }
alpar@780
  1025
    
alpar@780
  1026
  };
alpar@780
  1027
  
alpar@1218
  1028
  ///Function type interface for Dfs algorithm.
alpar@1218
  1029
alpar@1218
  1030
  /// \ingroup flowalgs
alpar@1218
  1031
  ///Function type interface for Dfs algorithm.
alpar@1218
  1032
  ///
alpar@1218
  1033
  ///This function also has several
alpar@1218
  1034
  ///\ref named-templ-func-param "named parameters",
alpar@1218
  1035
  ///they are declared as the members of class \ref DfsWizard.
alpar@1218
  1036
  ///The following
alpar@1218
  1037
  ///example shows how to use these parameters.
alpar@1218
  1038
  ///\code
alpar@1218
  1039
  ///  dfs(g,source).predMap(preds).run();
alpar@1218
  1040
  ///\endcode
alpar@1218
  1041
  ///\warning Don't forget to put the \ref DfsWizard::run() "run()"
alpar@1218
  1042
  ///to the end of the parameter list.
alpar@1218
  1043
  ///\sa DfsWizard
alpar@1218
  1044
  ///\sa Dfs
alpar@1218
  1045
  template<class GR>
alpar@1218
  1046
  DfsWizard<DfsWizardBase<GR> >
alpar@1218
  1047
  dfs(const GR &g,typename GR::Node s=INVALID)
alpar@1218
  1048
  {
alpar@1218
  1049
    return DfsWizard<DfsWizardBase<GR> >(g,s);
alpar@1218
  1050
  }
alpar@1218
  1051
deba@1799
  1052
#ifdef DOXYGEN
deba@1749
  1053
  /// \brief Visitor class for dfs.
deba@1749
  1054
  ///  
deba@1749
  1055
  /// It gives a simple interface for a functional interface for dfs 
deba@1749
  1056
  /// traversal. The traversal on a linear data structure. 
deba@1749
  1057
  template <typename _Graph>
deba@1749
  1058
  struct DfsVisitor {
deba@1749
  1059
    typedef _Graph Graph;
deba@1749
  1060
    typedef typename Graph::Edge Edge;
deba@1749
  1061
    typedef typename Graph::Node Node;
deba@1749
  1062
    /// \brief Called when the edge reach a node.
deba@1749
  1063
    /// 
deba@1749
  1064
    /// It is called when the dfs find an edge which target is not
deba@1749
  1065
    /// reached yet.
deba@1749
  1066
    void discover(const Edge& edge) {}
deba@1749
  1067
    /// \brief Called when the node reached first time.
deba@1749
  1068
    /// 
deba@1749
  1069
    /// It is Called when the node reached first time.
deba@1749
  1070
    void reach(const Node& node) {}
deba@1749
  1071
    /// \brief Called when we step back on an edge.
deba@1749
  1072
    /// 
deba@1749
  1073
    /// It is called when the dfs should step back on the edge.
deba@1749
  1074
    void backtrack(const Edge& edge) {}
deba@1749
  1075
    /// \brief Called when we step back from the node.
deba@1749
  1076
    /// 
deba@1749
  1077
    /// It is called when we step back from the node.
deba@1749
  1078
    void leave(const Node& node) {}
deba@1749
  1079
    /// \brief Called when the edge examined but target of the edge 
deba@1749
  1080
    /// already discovered.
deba@1749
  1081
    /// 
deba@1749
  1082
    /// It called when the edge examined but the target of the edge 
deba@1749
  1083
    /// already discovered.
deba@1749
  1084
    void examine(const Edge& edge) {}
deba@1749
  1085
    /// \brief Called for the source node of the dfs.
deba@1749
  1086
    /// 
deba@1749
  1087
    /// It is called for the source node of the dfs.
deba@1799
  1088
    void start(const Node& node) {}
deba@1749
  1089
    /// \brief Called when we leave the source node of the dfs.
deba@1749
  1090
    /// 
deba@1749
  1091
    /// It is called when we leave the source node of the dfs.
deba@1799
  1092
    void stop(const Node& node) {}
deba@1799
  1093
deba@1799
  1094
  };
deba@1799
  1095
#else
deba@1799
  1096
  template <typename _Graph>
deba@1799
  1097
  struct DfsVisitor {
deba@1799
  1098
    typedef _Graph Graph;
deba@1799
  1099
    typedef typename Graph::Edge Edge;
deba@1799
  1100
    typedef typename Graph::Node Node;
deba@1799
  1101
    void discover(const Edge&) {}
deba@1799
  1102
    void reach(const Node&) {}
deba@1799
  1103
    void backtrack(const Edge&) {}
deba@1799
  1104
    void leave(const Node&) {}
deba@1799
  1105
    void examine(const Edge&) {}
deba@1799
  1106
    void start(const Node&) {}
deba@1749
  1107
    void stop(const Node&) {}
deba@1749
  1108
deba@1749
  1109
    template <typename _Visitor>
deba@1749
  1110
    struct Constraints {
deba@1749
  1111
      void constraints() {
deba@1749
  1112
	Edge edge;
deba@1749
  1113
	Node node;
deba@1749
  1114
	visitor.discover(edge);
deba@1749
  1115
	visitor.reach(node);
deba@1749
  1116
	visitor.backtrack(edge);
deba@1749
  1117
	visitor.leave(node);
deba@1749
  1118
	visitor.examine(edge);
deba@1749
  1119
	visitor.start(node);
deba@1749
  1120
	visitor.stop(edge);
deba@1749
  1121
      }
deba@1749
  1122
      _Visitor& visitor;
deba@1749
  1123
    };
deba@1749
  1124
  };
deba@1799
  1125
#endif
deba@1749
  1126
deba@1749
  1127
  /// \brief Default traits class of DfsVisit class.
deba@1749
  1128
  ///
deba@1749
  1129
  /// Default traits class of DfsVisit class.
deba@1749
  1130
  /// \param _Graph Graph type.
deba@1749
  1131
  template<class _Graph>
deba@1749
  1132
  struct DfsVisitDefaultTraits {
deba@1749
  1133
deba@1749
  1134
    /// \brief The graph type the algorithm runs on. 
deba@1749
  1135
    typedef _Graph Graph;
deba@1749
  1136
deba@1749
  1137
    /// \brief The type of the map that indicates which nodes are reached.
deba@1749
  1138
    /// 
deba@1749
  1139
    /// The type of the map that indicates which nodes are reached.
deba@1749
  1140
    /// It must meet the \ref concept::WriteMap "WriteMap" concept.
deba@1749
  1141
    /// \todo named parameter to set this type, function to read and write.
deba@1749
  1142
    typedef typename Graph::template NodeMap<bool> ReachedMap;
deba@1749
  1143
deba@1749
  1144
    /// \brief Instantiates a ReachedMap.
deba@1749
  1145
    ///
deba@1749
  1146
    /// This function instantiates a \ref ReachedMap. 
deba@1749
  1147
    /// \param G is the graph, to which
deba@1749
  1148
    /// we would like to define the \ref ReachedMap.
deba@1749
  1149
    static ReachedMap *createReachedMap(const Graph &graph) {
deba@1749
  1150
      return new ReachedMap(graph);
deba@1749
  1151
    }
deba@1749
  1152
deba@1749
  1153
  };
deba@1749
  1154
  
deba@1749
  1155
  /// %DFS Visit algorithm class.
deba@1749
  1156
  
deba@1749
  1157
  /// \ingroup flowalgs
deba@1749
  1158
  /// This class provides an efficient implementation of the %DFS algorithm
deba@1749
  1159
  /// with visitor interface.
deba@1749
  1160
  ///
deba@1749
  1161
  /// The %DfsVisit class provides an alternative interface to the Dfs
deba@1749
  1162
  /// class. It works with callback mechanism, the DfsVisit object calls
deba@1749
  1163
  /// on every dfs event the \c Visitor class member functions. 
deba@1749
  1164
  ///
deba@1749
  1165
  /// \param _Graph The graph type the algorithm runs on. The default value is
deba@1749
  1166
  /// \ref ListGraph. The value of _Graph is not used directly by Dfs, it
deba@1749
  1167
  /// is only passed to \ref DfsDefaultTraits.
deba@1749
  1168
  /// \param _Visitor The Visitor object for the algorithm. The 
deba@1749
  1169
  /// \ref DfsVisitor "DfsVisitor<_Graph>" is an empty Visitor which
deba@1749
  1170
  /// does not observe the Dfs events. If you want to observe the dfs
deba@1749
  1171
  /// events you should implement your own Visitor class.
deba@1749
  1172
  /// \param _Traits Traits class to set various data types used by the 
deba@1749
  1173
  /// algorithm. The default traits class is
deba@1749
  1174
  /// \ref DfsVisitDefaultTraits "DfsVisitDefaultTraits<_Graph>".
deba@1749
  1175
  /// See \ref DfsVisitDefaultTraits for the documentation of
deba@1749
  1176
  /// a Dfs visit traits class.
deba@1749
  1177
  ///
deba@1749
  1178
  /// \author Jacint Szabo, Alpar Juttner and Balazs Dezso
deba@1749
  1179
#ifdef DOXYGEN
deba@1749
  1180
  template <typename _Graph, typename _Visitor, typename _Traits>
deba@1749
  1181
#else
deba@1749
  1182
  template <typename _Graph = ListGraph,
deba@1749
  1183
	    typename _Visitor = DfsVisitor<_Graph>,
deba@1749
  1184
	    typename _Traits = DfsDefaultTraits<_Graph> >
deba@1749
  1185
#endif
deba@1749
  1186
  class DfsVisit {
deba@1749
  1187
  public:
deba@1749
  1188
    
deba@1749
  1189
    /// \brief \ref Exception for uninitialized parameters.
deba@1749
  1190
    ///
deba@1749
  1191
    /// This error represents problems in the initialization
deba@1749
  1192
    /// of the parameters of the algorithms.
deba@1749
  1193
    class UninitializedParameter : public lemon::UninitializedParameter {
deba@1749
  1194
    public:
deba@1749
  1195
      virtual const char* exceptionName() const {
deba@1749
  1196
	return "lemon::DfsVisit::UninitializedParameter";
deba@1749
  1197
      }
deba@1749
  1198
    };
deba@1749
  1199
deba@1749
  1200
    typedef _Traits Traits;
deba@1749
  1201
deba@1749
  1202
    typedef typename Traits::Graph Graph;
deba@1749
  1203
deba@1749
  1204
    typedef _Visitor Visitor;
deba@1749
  1205
deba@1749
  1206
    ///The type of the map indicating which nodes are reached.
deba@1749
  1207
    typedef typename Traits::ReachedMap ReachedMap;
deba@1749
  1208
deba@1749
  1209
  private:
deba@1749
  1210
deba@1749
  1211
    typedef typename Graph::Node Node;
deba@1749
  1212
    typedef typename Graph::NodeIt NodeIt;
deba@1749
  1213
    typedef typename Graph::Edge Edge;
deba@1749
  1214
    typedef typename Graph::OutEdgeIt OutEdgeIt;
deba@1749
  1215
deba@1749
  1216
    /// Pointer to the underlying graph.
deba@1749
  1217
    const Graph *_graph;
deba@1749
  1218
    /// Pointer to the visitor object.
deba@1749
  1219
    Visitor *_visitor;
deba@1749
  1220
    ///Pointer to the map of reached status of the nodes.
deba@1749
  1221
    ReachedMap *_reached;
deba@1749
  1222
    ///Indicates if \ref _reached is locally allocated (\c true) or not.
deba@1749
  1223
    bool local_reached;
deba@1749
  1224
deba@1749
  1225
    std::vector<typename Graph::Edge> _stack;
deba@1749
  1226
    int _stack_head;
deba@1749
  1227
deba@1749
  1228
    /// \brief Creates the maps if necessary.
deba@1749
  1229
    ///
deba@1749
  1230
    /// Creates the maps if necessary.
deba@1749
  1231
    void create_maps() {
deba@1749
  1232
      if(!_reached) {
deba@1749
  1233
	local_reached = true;
deba@1749
  1234
	_reached = Traits::createReachedMap(*_graph);
deba@1749
  1235
      }
deba@1749
  1236
    }
deba@1749
  1237
deba@1749
  1238
  protected:
deba@1749
  1239
deba@1749
  1240
    DfsVisit() {}
deba@1749
  1241
    
deba@1749
  1242
  public:
deba@1749
  1243
deba@1749
  1244
    typedef DfsVisit Create;
deba@1749
  1245
deba@1749
  1246
    /// \name Named template parameters
deba@1749
  1247
deba@1749
  1248
    ///@{
deba@1749
  1249
    template <class T>
deba@1749
  1250
    struct DefReachedMapTraits : public Traits {
deba@1749
  1251
      typedef T ReachedMap;
deba@1749
  1252
      static ReachedMap *createReachedMap(const Graph &graph) {
deba@1749
  1253
	throw UninitializedParameter();
deba@1749
  1254
      }
deba@1749
  1255
    };
deba@1749
  1256
    /// \brief \ref named-templ-param "Named parameter" for setting 
deba@1749
  1257
    /// ReachedMap type
deba@1749
  1258
    ///
deba@1749
  1259
    /// \ref named-templ-param "Named parameter" for setting ReachedMap type
deba@1749
  1260
    template <class T>
alpar@1773
  1261
    struct DefReachedMap : public DfsVisit< Graph, Visitor,
alpar@1773
  1262
					    DefReachedMapTraits<T> > {
alpar@1773
  1263
      typedef DfsVisit< Graph, Visitor, DefReachedMapTraits<T> > Create;
deba@1749
  1264
    };
deba@1749
  1265
    ///@}
deba@1749
  1266
deba@1749
  1267
  public:      
deba@1749
  1268
    
deba@1749
  1269
    /// \brief Constructor.
deba@1749
  1270
    ///
deba@1749
  1271
    /// Constructor.
deba@1749
  1272
    ///
deba@1749
  1273
    /// \param graph the graph the algorithm will run on.
deba@1749
  1274
    /// \param visitor The visitor of the algorithm.
deba@1749
  1275
    ///
deba@1749
  1276
    DfsVisit(const Graph& graph, Visitor& visitor) 
deba@1749
  1277
      : _graph(&graph), _visitor(&visitor),
deba@1749
  1278
	_reached(0), local_reached(false) {}
deba@1749
  1279
    
deba@1749
  1280
    /// \brief Destructor.
deba@1749
  1281
    ///
deba@1749
  1282
    /// Destructor.
deba@1749
  1283
    ~DfsVisit() {
deba@1749
  1284
      if(local_reached) delete _reached;
deba@1749
  1285
    }
deba@1749
  1286
deba@1749
  1287
    /// \brief Sets the map indicating if a node is reached.
deba@1749
  1288
    ///
deba@1749
  1289
    /// Sets the map indicating if a node is reached.
deba@1749
  1290
    /// If you don't use this function before calling \ref run(),
deba@1749
  1291
    /// it will allocate one. The destuctor deallocates this
deba@1749
  1292
    /// automatically allocated map, of course.
deba@1749
  1293
    /// \return <tt> (*this) </tt>
deba@1749
  1294
    DfsVisit &reachedMap(ReachedMap &m) {
deba@1749
  1295
      if(local_reached) {
deba@1749
  1296
	delete _reached;
deba@1749
  1297
	local_reached=false;
deba@1749
  1298
      }
deba@1749
  1299
      _reached = &m;
deba@1749
  1300
      return *this;
deba@1749
  1301
    }
deba@1749
  1302
deba@1749
  1303
  public:
deba@1749
  1304
    /// \name Execution control
deba@1749
  1305
    /// The simplest way to execute the algorithm is to use
deba@1749
  1306
    /// one of the member functions called \c run(...).
deba@1749
  1307
    /// \n
deba@1749
  1308
    /// If you need more control on the execution,
deba@1761
  1309
    /// first you must call \ref init(), then you can adda source node
deba@1749
  1310
    /// with \ref addSource().
deba@1749
  1311
    /// Finally \ref start() will perform the actual path
deba@1749
  1312
    /// computation.
deba@1749
  1313
deba@1749
  1314
    /// @{
deba@1749
  1315
    /// \brief Initializes the internal data structures.
deba@1749
  1316
    ///
deba@1749
  1317
    /// Initializes the internal data structures.
deba@1749
  1318
    ///
deba@1749
  1319
    void init() {
deba@1749
  1320
      create_maps();
deba@1749
  1321
      _stack.resize(countNodes(*_graph));
deba@1749
  1322
      _stack_head = -1;
deba@1749
  1323
      for (NodeIt u(*_graph) ; u != INVALID ; ++u) {
deba@1749
  1324
	_reached->set(u, false);
deba@1749
  1325
      }
deba@1749
  1326
    }
deba@1749
  1327
    
deba@1749
  1328
    /// \brief Adds a new source node.
deba@1749
  1329
    ///
deba@1749
  1330
    /// Adds a new source node to the set of nodes to be processed.
deba@1749
  1331
    void addSource(Node s) {
deba@1749
  1332
      if(!(*_reached)[s]) {
deba@1749
  1333
	  _reached->set(s,true);
deba@1749
  1334
	  _visitor->start(s);
deba@1749
  1335
	  _visitor->reach(s);
deba@1749
  1336
	  Edge e; 
deba@1749
  1337
	  _graph->firstOut(e, s);
deba@1749
  1338
	  if (e != INVALID) {
deba@1749
  1339
	    _stack[++_stack_head] = e;
deba@1749
  1340
	  } else {
deba@1749
  1341
	    _visitor->leave(s);
deba@1749
  1342
	  }
deba@1749
  1343
	}
deba@1749
  1344
    }
deba@1749
  1345
    
deba@1749
  1346
    /// \brief Processes the next edge.
deba@1749
  1347
    ///
deba@1749
  1348
    /// Processes the next edge.
deba@1749
  1349
    ///
deba@1749
  1350
    /// \return The processed edge.
deba@1749
  1351
    ///
deba@1749
  1352
    /// \pre The stack must not be empty!
deba@1749
  1353
    Edge processNextEdge() { 
deba@1749
  1354
      Edge e = _stack[_stack_head];
deba@1749
  1355
      Node m = _graph->target(e);
deba@1749
  1356
      if(!(*_reached)[m]) {
deba@1749
  1357
	_visitor->discover(e);
deba@1749
  1358
	_visitor->reach(m);
deba@1749
  1359
	_reached->set(m, true);
deba@1749
  1360
	_graph->firstOut(_stack[++_stack_head], m);
deba@1749
  1361
      } else {
deba@1749
  1362
	_visitor->examine(e);
deba@1749
  1363
	m = _graph->source(e);
deba@1749
  1364
	_graph->nextOut(_stack[_stack_head]);
deba@1749
  1365
      }
deba@1749
  1366
      while (_stack_head>=0 && _stack[_stack_head] == INVALID) {
deba@1749
  1367
	_visitor->leave(m);
deba@1749
  1368
	--_stack_head;
deba@1749
  1369
	if (_stack_head >= 0) {
deba@1749
  1370
	  _visitor->backtrack(_stack[_stack_head]);
deba@1749
  1371
	  m = _graph->source(_stack[_stack_head]);
deba@1749
  1372
	  _graph->nextOut(_stack[_stack_head]);
deba@1749
  1373
	} else {
deba@1749
  1374
	  _visitor->stop(m);	  
deba@1749
  1375
	}
deba@1749
  1376
      }
deba@1749
  1377
      return e;
deba@1749
  1378
    }
deba@1749
  1379
deba@1749
  1380
    /// \brief Next edge to be processed.
deba@1749
  1381
    ///
deba@1749
  1382
    /// Next edge to be processed.
deba@1749
  1383
    ///
deba@1749
  1384
    /// \return The next edge to be processed or INVALID if the stack is
deba@1749
  1385
    /// empty.
deba@1749
  1386
    Edge nextEdge() { 
deba@1749
  1387
      return _stack_head >= 0 ? _stack[_stack_head] : INVALID;
deba@1749
  1388
    }
deba@1749
  1389
deba@1749
  1390
    /// \brief Returns \c false if there are nodes
deba@1749
  1391
    /// to be processed in the queue
deba@1749
  1392
    ///
deba@1749
  1393
    /// Returns \c false if there are nodes
deba@1749
  1394
    /// to be processed in the queue
deba@1749
  1395
    bool emptyQueue() { return _stack_head < 0; }
deba@1749
  1396
deba@1749
  1397
    /// \brief Returns the number of the nodes to be processed.
deba@1749
  1398
    ///
deba@1749
  1399
    /// Returns the number of the nodes to be processed in the queue.
deba@1749
  1400
    int queueSize() { return _stack_head + 1; }
deba@1749
  1401
    
deba@1749
  1402
    /// \brief Executes the algorithm.
deba@1749
  1403
    ///
deba@1749
  1404
    /// Executes the algorithm.
deba@1749
  1405
    ///
deba@1749
  1406
    /// \pre init() must be called and at least one node should be added
deba@1749
  1407
    /// with addSource() before using this function.
deba@1749
  1408
    void start() {
deba@1749
  1409
      while ( !emptyQueue() ) processNextEdge();
deba@1749
  1410
    }
deba@1749
  1411
    
deba@1749
  1412
    /// \brief Executes the algorithm until \c dest is reached.
deba@1749
  1413
    ///
deba@1749
  1414
    /// Executes the algorithm until \c dest is reached.
deba@1749
  1415
    ///
deba@1749
  1416
    /// \pre init() must be called and at least one node should be added
deba@1749
  1417
    /// with addSource() before using this function.
deba@1749
  1418
    void start(Node dest) {
deba@1749
  1419
      while ( !emptyQueue() && _graph->target(_stack[_stack_head]) != dest) 
deba@1749
  1420
	processNextEdge();
deba@1749
  1421
    }
deba@1749
  1422
    
deba@1749
  1423
    /// \brief Executes the algorithm until a condition is met.
deba@1749
  1424
    ///
deba@1749
  1425
    /// Executes the algorithm until a condition is met.
deba@1749
  1426
    ///
deba@1749
  1427
    /// \pre init() must be called and at least one node should be added
deba@1749
  1428
    /// with addSource() before using this function.
deba@1749
  1429
    ///
deba@1749
  1430
    /// \param nm must be a bool (or convertible) edge map. The algorithm
deba@1749
  1431
    /// will stop when it reaches an edge \c e with <tt>nm[e]==true</tt>.
deba@1749
  1432
    ///
deba@1749
  1433
    /// \warning Contrary to \ref Dfs and \ref Dijkstra, \c em is an edge map,
deba@1749
  1434
    /// not a node map.
deba@1749
  1435
    template <typename EM>
deba@1749
  1436
    void start(const EM &em) {
deba@1749
  1437
      while (!emptyQueue() && !em[_stack[_stack_head]]) processNextEdge();
deba@1749
  1438
    }
deba@1749
  1439
deba@1749
  1440
    /// \brief Runs %DFS algorithm from node \c s.
deba@1749
  1441
    ///
deba@1749
  1442
    /// This method runs the %DFS algorithm from a root node \c s.
deba@1749
  1443
    /// \note d.run(s) is just a shortcut of the following code.
deba@1749
  1444
    /// \code
deba@1749
  1445
    ///   d.init();
deba@1749
  1446
    ///   d.addSource(s);
deba@1749
  1447
    ///   d.start();
deba@1749
  1448
    /// \endcode
deba@1749
  1449
    void run(Node s) {
deba@1749
  1450
      init();
deba@1749
  1451
      addSource(s);
deba@1749
  1452
      start();
deba@1749
  1453
    }
deba@1749
  1454
    ///@}
deba@1749
  1455
deba@1749
  1456
    /// \name Query Functions
deba@1749
  1457
    /// The result of the %DFS algorithm can be obtained using these
deba@1749
  1458
    /// functions.\n
deba@1749
  1459
    /// Before the use of these functions,
deba@1749
  1460
    /// either run() or start() must be called.
deba@1749
  1461
    ///@{
deba@1749
  1462
    /// \brief Checks if a node is reachable from the root.
deba@1749
  1463
    ///
deba@1749
  1464
    /// Returns \c true if \c v is reachable from the root(s).
deba@1749
  1465
    /// \warning The source nodes are inditated as unreachable.
deba@1749
  1466
    /// \pre Either \ref run() or \ref start()
deba@1749
  1467
    /// must be called before using this function.
deba@1749
  1468
    ///
deba@1749
  1469
    bool reached(Node v) { return (*_reached)[v]; }
deba@1749
  1470
    ///@}
deba@1749
  1471
  };
deba@1749
  1472
deba@1749
  1473
alpar@921
  1474
} //END OF NAMESPACE LEMON
alpar@780
  1475
alpar@780
  1476
#endif
alpar@780
  1477