src/work/alpar/dijkstra.h
changeset 1131 425731cb66de
parent 1128 6a347310d4c2
equal deleted inserted replaced
16:bf1533bdc053 17:64907c0a845e
    83     ///
    83     ///
    84     ///The type of the map that stores the last but one
    84     ///The type of the map that stores the last but one
    85     ///nodes of the shortest paths.
    85     ///nodes of the shortest paths.
    86     ///It must meet the \ref concept::WriteMap "WriteMap" concept.
    86     ///It must meet the \ref concept::WriteMap "WriteMap" concept.
    87     ///
    87     ///
    88     typedef typename Graph::template NodeMap<typename GR::Node> PredNodeMap;
    88     typedef NullMap<typename Graph::Node,typename Graph::Node> PredNodeMap;
    89     ///Instantiates a PredNodeMap.
    89     ///Instantiates a PredNodeMap.
    90     
    90     
    91     ///This function instantiates a \ref PredNodeMap. 
    91     ///This function instantiates a \ref PredNodeMap. 
    92     ///\param G is the graph, to which we would like to define the \ref PredNodeMap
    92     ///\param G is the graph, to which we would like to define the \ref PredNodeMap
    93     static PredNodeMap *createPredNodeMap(const GR &G)
    93     static PredNodeMap *createPredNodeMap(const GR &G)
    94     {
    94     {
    95       return new PredNodeMap(G);
    95       return new PredNodeMap();
    96     }
    96     }
    97 
    97 
    98     ///The type of the map that stores whether a nodes is reached.
    98     ///The type of the map that stores whether a nodes is reached.
    99  
    99  
   100     ///The type of the map that stores whether a nodes is reached.
   100     ///The type of the map that stores whether a nodes is reached.
   220     ///Pointer to the map of predecessors edges.
   220     ///Pointer to the map of predecessors edges.
   221     PredMap *_pred;
   221     PredMap *_pred;
   222     ///Indicates if \ref _pred is locally allocated (\c true) or not.
   222     ///Indicates if \ref _pred is locally allocated (\c true) or not.
   223     bool local_pred;
   223     bool local_pred;
   224     ///Pointer to the map of predecessors nodes.
   224     ///Pointer to the map of predecessors nodes.
   225     PredNodeMap *pred_node;
   225     PredNodeMap *_predNode;
   226     ///Indicates if \ref pred_node is locally allocated (\c true) or not.
   226     ///Indicates if \ref _predNode is locally allocated (\c true) or not.
   227     bool local_pred_node;
   227     bool local_predNode;
   228     ///Pointer to the map of distances.
   228     ///Pointer to the map of distances.
   229     DistMap *distance;
   229     DistMap *_dist;
   230     ///Indicates if \ref distance is locally allocated (\c true) or not.
   230     ///Indicates if \ref _dist is locally allocated (\c true) or not.
   231     bool local_distance;
   231     bool local_dist;
   232     ///Pointer to the map of reached status of the nodes.
   232     ///Pointer to the map of reached status of the nodes.
   233     ReachedMap *_reached;
   233     ReachedMap *_reached;
   234     ///Indicates if \ref _reached is locally allocated (\c true) or not.
   234     ///Indicates if \ref _reached is locally allocated (\c true) or not.
   235     bool local_reached;
   235     bool local_reached;
   236 
   236 
   245     {
   245     {
   246       if(!_pred) {
   246       if(!_pred) {
   247 	local_pred = true;
   247 	local_pred = true;
   248 	_pred = Traits::createPredMap(*G);
   248 	_pred = Traits::createPredMap(*G);
   249       }
   249       }
   250       if(!pred_node) {
   250       if(!_predNode) {
   251 	local_pred_node = true;
   251 	local_predNode = true;
   252 	pred_node = Traits::createPredNodeMap(*G);
   252 	_predNode = Traits::createPredNodeMap(*G);
   253       }
   253       }
   254       if(!distance) {
   254       if(!_dist) {
   255 	local_distance = true;
   255 	local_dist = true;
   256 	distance = Traits::createDistMap(*G);
   256 	_dist = Traits::createDistMap(*G);
   257       }
   257       }
   258       if(!_reached) {
   258       if(!_reached) {
   259 	local_reached = true;
   259 	local_reached = true;
   260 	_reached = Traits::createReachedMap(*G);
   260 	_reached = Traits::createReachedMap(*G);
   261       }
   261       }
   367     ///\param _G the graph the algorithm will run on.
   367     ///\param _G the graph the algorithm will run on.
   368     ///\param _length the length map used by the algorithm.
   368     ///\param _length the length map used by the algorithm.
   369     Dijkstra(const Graph& _G, const LengthMap& _length) :
   369     Dijkstra(const Graph& _G, const LengthMap& _length) :
   370       G(&_G), length(&_length),
   370       G(&_G), length(&_length),
   371       _pred(NULL), local_pred(false),
   371       _pred(NULL), local_pred(false),
   372       pred_node(NULL), local_pred_node(false),
   372       _predNode(NULL), local_predNode(false),
   373       distance(NULL), local_distance(false),
   373       _dist(NULL), local_dist(false),
   374       _reached(NULL), local_reached(false),
   374       _reached(NULL), local_reached(false),
   375       _heap_map(*G,-1),_heap(_heap_map)
   375       _heap_map(*G,-1),_heap(_heap_map)
   376     { }
   376     { }
   377     
   377     
   378     ///Destructor.
   378     ///Destructor.
   379     ~Dijkstra() 
   379     ~Dijkstra() 
   380     {
   380     {
   381       if(local_pred) delete _pred;
   381       if(local_pred) delete _pred;
   382       if(local_pred_node) delete pred_node;
   382       if(local_predNode) delete _predNode;
   383       if(local_distance) delete distance;
   383       if(local_dist) delete _dist;
   384       if(local_reached) delete _reached;
   384       if(local_reached) delete _reached;
   385     }
   385     }
   386 
   386 
   387     ///Sets the length map.
   387     ///Sets the length map.
   388 
   388 
   418     ///it will allocate one. The destuctor deallocates this
   418     ///it will allocate one. The destuctor deallocates this
   419     ///automatically allocated map, of course.
   419     ///automatically allocated map, of course.
   420     ///\return <tt> (*this) </tt>
   420     ///\return <tt> (*this) </tt>
   421     Dijkstra &predNodeMap(PredNodeMap &m) 
   421     Dijkstra &predNodeMap(PredNodeMap &m) 
   422     {
   422     {
   423       if(local_pred_node) {
   423       if(local_predNode) {
   424 	delete pred_node;
   424 	delete _predNode;
   425 	local_pred_node=false;
   425 	local_predNode=false;
   426       }
   426       }
   427       pred_node = &m;
   427       _predNode = &m;
   428       return *this;
   428       return *this;
   429     }
   429     }
   430 
   430 
   431     ///Sets the map storing the distances calculated by the algorithm.
   431     ///Sets the map storing the distances calculated by the algorithm.
   432 
   432 
   435     ///it will allocate one. The destuctor deallocates this
   435     ///it will allocate one. The destuctor deallocates this
   436     ///automatically allocated map, of course.
   436     ///automatically allocated map, of course.
   437     ///\return <tt> (*this) </tt>
   437     ///\return <tt> (*this) </tt>
   438     Dijkstra &distMap(DistMap &m) 
   438     Dijkstra &distMap(DistMap &m) 
   439     {
   439     {
   440       if(local_distance) {
   440       if(local_dist) {
   441 	delete distance;
   441 	delete _dist;
   442 	local_distance=false;
   442 	local_dist=false;
   443       }
   443       }
   444       distance = &m;
   444       _dist = &m;
   445       return *this;
   445       return *this;
   446     }
   446     }
   447 
   447 
       
   448   private:
       
   449     void finalizeNodeData(Node v,Value dst)
       
   450     {
       
   451       _reached->set(v,true);
       
   452       _dist->set(v, dst);
       
   453       _predNode->set(v,G->source((*_pred)[v]));
       
   454     }
       
   455 
       
   456   public:
   448     ///\name Excetution control
   457     ///\name Excetution control
   449     ///The simplest way to execute the algorithm is to use
   458     ///The simplest way to execute the algorithm is to use
   450     ///\ref run().
   459     ///\ref run().
   451     ///\n
   460     ///\n
   452     ///It you need more control on the execution,
   461     ///It you need more control on the execution,
   465     {
   474     {
   466       create_maps();
   475       create_maps();
   467       
   476       
   468       for ( NodeIt u(*G) ; u!=INVALID ; ++u ) {
   477       for ( NodeIt u(*G) ; u!=INVALID ; ++u ) {
   469 	_pred->set(u,INVALID);
   478 	_pred->set(u,INVALID);
   470 	pred_node->set(u,INVALID);
   479 	_predNode->set(u,INVALID);
   471 	///\todo *_reached is not set to false.
   480 	///\todo *_reached is not set to false.
   472 	_heap_map.set(u,Heap::PRE_HEAP);
   481 	_heap_map.set(u,Heap::PRE_HEAP);
   473       }
   482       }
   474     }
   483     }
   475     
   484     
   488     }
   497     }
   489     
   498     
   490     void processNode()
   499     void processNode()
   491     {
   500     {
   492       Node v=_heap.top(); 
   501       Node v=_heap.top(); 
   493       _reached->set(v,true);
       
   494       Value oldvalue=_heap[v];
   502       Value oldvalue=_heap[v];
   495       _heap.pop();
   503       _heap.pop();
   496       distance->set(v, oldvalue);
   504       finalizeNodeData(v,oldvalue);
   497       
   505       
   498       for(OutEdgeIt e(*G,v); e!=INVALID; ++e) {
   506       for(OutEdgeIt e(*G,v); e!=INVALID; ++e) {
   499 	Node w=G->target(e); 
   507 	Node w=G->target(e); 
   500 	switch(_heap.state(w)) {
   508 	switch(_heap.state(w)) {
   501 	case Heap::PRE_HEAP:
   509 	case Heap::PRE_HEAP:
   502 	  _heap.push(w,oldvalue+(*length)[e]); 
   510 	  _heap.push(w,oldvalue+(*length)[e]); 
   503 	  _pred->set(w,e);
   511 	  _pred->set(w,e);
   504 	  pred_node->set(w,v);
   512 //  	  _predNode->set(w,v);
   505 	  break;
   513 	  break;
   506 	case Heap::IN_HEAP:
   514 	case Heap::IN_HEAP:
   507 	  if ( oldvalue+(*length)[e] < _heap[w] ) {
   515 	  if ( oldvalue+(*length)[e] < _heap[w] ) {
   508 	    _heap.decrease(w, oldvalue+(*length)[e]); 
   516 	    _heap.decrease(w, oldvalue+(*length)[e]); 
   509 	    _pred->set(w,e);
   517 	    _pred->set(w,e);
   510 	    pred_node->set(w,v);
   518 // 	    _predNode->set(w,v);
   511 	  }
   519 	  }
   512 	  break;
   520 	  break;
   513 	case Heap::POST_HEAP:
   521 	case Heap::POST_HEAP:
   514 	  break;
   522 	  break;
   515 	}
   523 	}
   516       }
   524       }
   517     }
   525     }
   518 
   526 
   519     ///Starts the execution of the algorithm.
   527     ///Executes the algorithm.
   520 
   528 
   521     ///Starts the execution of the algorithm.
   529     ///Executes the algorithm.
   522     ///
   530     ///
   523     ///\pre init() must be called before and at least one node should be added
   531     ///\pre init() must be called and at least one node should be added
   524     ///with addSource().
   532     ///with addSource() before using this function.
   525     ///
   533     ///
   526     ///This method runs the %Dijkstra algorithm from the root node(s)
   534     ///This method runs the %Dijkstra algorithm from the root node(s)
   527     ///in order to
   535     ///in order to
   528     ///compute the
   536     ///compute the
   529     ///shortest path to each node. The algorithm computes
   537     ///shortest path to each node. The algorithm computes
   533     void start()
   541     void start()
   534     {
   542     {
   535       while ( !_heap.empty() ) processNode();
   543       while ( !_heap.empty() ) processNode();
   536     }
   544     }
   537     
   545     
   538     ///Starts the execution of the algorithm until \c dest is reached.
   546     ///Executes the algorithm until \c dest is reached.
   539 
   547 
   540     ///Starts the execution of the algorithm until \c dest is reached.
   548     ///Executes the algorithm until \c dest is reached.
   541     ///
   549     ///
   542     ///\pre init() must be called before and at least one node should be added
   550     ///\pre init() must be called and at least one node should be added
   543     ///with addSource().
   551     ///with addSource() before using this function.
   544     ///
   552     ///
   545     ///This method runs the %Dijkstra algorithm from the root node(s)
   553     ///This method runs the %Dijkstra algorithm from the root node(s)
   546     ///in order to
   554     ///in order to
   547     ///compute the
   555     ///compute the
   548     ///shortest path to \c dest. The algorithm computes
   556     ///shortest path to \c dest. The algorithm computes
   549     ///- The shortest path to \c  dest.
   557     ///- The shortest path to \c  dest.
   550     ///- The distance of \c dest from the root(s).
   558     ///- The distance of \c dest from the root(s).
   551     ///
   559     ///
   552     void start(Node dest)
   560     void start(Node dest)
   553     {
   561     {
   554       while ( !_heap.empty() && _heap.top()!=dest) processNode();
   562       while ( !_heap.empty() && _heap.top()!=dest ) processNode();
       
   563       if ( _heap.top()==dest ) finalizeNodeData(_heap.top());
       
   564     }
       
   565     
       
   566     ///Executes the algorithm until a condition is met.
       
   567 
       
   568     ///Executes the algorithm until a condition is met.
       
   569     ///
       
   570     ///\pre init() must be called and at least one node should be added
       
   571     ///with addSource() before using this function.
       
   572     ///
       
   573     ///\param nm must be a bool (or convertible) node map. The algorithm
       
   574     ///will stop when it reaches a node \c v with <tt>nm[v]==true</tt>.
       
   575     template<class NM>
       
   576     void start(const NM &nm)
       
   577     {
       
   578       while ( !_heap.empty() && !mn[_heap.top()] ) processNode();
       
   579       if ( !_heap.empty() ) finalizeNodeData(_heap.top());
   555     }
   580     }
   556     
   581     
   557     ///Runs %Dijkstra algorithm from node \c s.
   582     ///Runs %Dijkstra algorithm from node \c s.
   558     
   583     
   559     ///This method runs the %Dijkstra algorithm from a root node \c s
   584     ///This method runs the %Dijkstra algorithm from a root node \c s
   573       init();
   598       init();
   574       addSource(s);
   599       addSource(s);
   575       start();
   600       start();
   576     }
   601     }
   577     
   602     
       
   603     ///Finds the shortest path between \c s and \c t.
       
   604     
       
   605     ///Finds the shortest path between \c s and \c t.
       
   606     ///
       
   607     ///\return The length of the shortest s---t path if there exists one,
       
   608     ///0 otherwise.
       
   609     ///\note Apart from the return value, d.run(s) is
       
   610     ///just a shortcut of the following code.
       
   611     ///\code
       
   612     ///  d.init();
       
   613     ///  d.addSource(s);
       
   614     ///  d.start(t);
       
   615     ///\endcode
       
   616     Value run(Node s,Node t) {
       
   617       init();
       
   618       addSource(s);
       
   619       start(t);
       
   620       return (*_pred)[t]==INVALID?0:(*_dist)[t];
       
   621     }
       
   622     
   578     ///@}
   623     ///@}
   579 
   624 
   580     ///\name Query Functions
   625     ///\name Query Functions
   581     ///The result of the %Dijkstra algorithm can be obtained using these
   626     ///The result of the %Dijkstra algorithm can be obtained using these
   582     ///functions.\n
   627     ///functions.\n
   589 
   634 
   590     ///Returns the distance of a node from the root.
   635     ///Returns the distance of a node from the root.
   591     ///\pre \ref run() must be called before using this function.
   636     ///\pre \ref run() must be called before using this function.
   592     ///\warning If node \c v in unreachable from the root the return value
   637     ///\warning If node \c v in unreachable from the root the return value
   593     ///of this funcion is undefined.
   638     ///of this funcion is undefined.
   594     Value dist(Node v) const { return (*distance)[v]; }
   639     Value dist(Node v) const { return (*_dist)[v]; }
   595 
   640 
   596     ///Returns the 'previous edge' of the shortest path tree.
   641     ///Returns the 'previous edge' of the shortest path tree.
   597 
   642 
   598     ///For a node \c v it returns the 'previous edge' of the shortest path tree,
   643     ///For a node \c v it returns the 'previous edge' of the shortest path tree,
   599     ///i.e. it returns the last edge of a shortest path from the root to \c
   644     ///i.e. it returns the last edge of a shortest path from the root to \c
   611     ///i.e. it returns the last but one node from a shortest path from the
   656     ///i.e. it returns the last but one node from a shortest path from the
   612     ///root to \c /v. It is INVALID if \c v is unreachable from the root or if
   657     ///root to \c /v. It is INVALID if \c v is unreachable from the root or if
   613     ///\c v=s. The shortest path tree used here is equal to the shortest path
   658     ///\c v=s. The shortest path tree used here is equal to the shortest path
   614     ///tree used in \ref pred(Node v).  \pre \ref run() must be called before
   659     ///tree used in \ref pred(Node v).  \pre \ref run() must be called before
   615     ///using this function.
   660     ///using this function.
   616     Node predNode(Node v) const { return (*pred_node)[v]; }
   661     Node predNode(Node v) const { return (*_pred)[v]==INVALID ? INVALID:
       
   662 				  G->source((*_pred)[v]); }
   617     
   663     
   618     ///Returns a reference to the NodeMap of distances.
   664     ///Returns a reference to the NodeMap of distances.
   619 
   665 
   620     ///Returns a reference to the NodeMap of distances. \pre \ref run() must
   666     ///Returns a reference to the NodeMap of distances. \pre \ref run() must
   621     ///be called before using this function.
   667     ///be called before using this function.
   622     const DistMap &distMap() const { return *distance;}
   668     const DistMap &distMap() const { return *_dist;}
   623  
   669  
   624     ///Returns a reference to the shortest path tree map.
   670     ///Returns a reference to the shortest path tree map.
   625 
   671 
   626     ///Returns a reference to the NodeMap of the edges of the
   672     ///Returns a reference to the NodeMap of the edges of the
   627     ///shortest path tree.
   673     ///shortest path tree.
   631     ///Returns a reference to the map of nodes of shortest paths.
   677     ///Returns a reference to the map of nodes of shortest paths.
   632 
   678 
   633     ///Returns a reference to the NodeMap of the last but one nodes of the
   679     ///Returns a reference to the NodeMap of the last but one nodes of the
   634     ///shortest path tree.
   680     ///shortest path tree.
   635     ///\pre \ref run() must be called before using this function.
   681     ///\pre \ref run() must be called before using this function.
   636     const PredNodeMap &predNodeMap() const { return *pred_node;}
   682     const PredNodeMap &predNodeMap() const { return *_predNode;}
   637 
   683 
   638     ///Checks if a node is reachable from the root.
   684     ///Checks if a node is reachable from the root.
   639 
   685 
   640     ///Returns \c true if \c v is reachable from the root.
   686     ///Returns \c true if \c v is reachable from the root.
   641     ///\warning If the algorithm is started from multiple nodes,
   687     ///\warning If the algorithm is started from multiple nodes,