# HG changeset patch
# User alpar
# Date 1169461334 0
# Node ID 5ef61c97bf1bdf9d5e8b9883148a09622f994434
# Parent  0aaa7ada53958d9c9072d9163029971fde375716
- Some bugfixes
- Better doc
- liftToTop(), liftTo() added

diff -r 0aaa7ada5395 -r 5ef61c97bf1b lemon/elevator.h
--- a/lemon/elevator.h	Fri Jan 19 17:27:22 2007 +0000
+++ b/lemon/elevator.h	Mon Jan 22 10:22:14 2007 +0000
@@ -86,7 +86,7 @@
       *j=ti;
     }
     
-    void checkDs() 
+    void checkDs() const
     {
       for(typename ItemSetTraits<Graph,Item>::ItemIt i(_g);i!=INVALID;++i)
 	{
@@ -96,6 +96,12 @@
 	  check(_first[l]<=w,"GEBASZ: CORRUPT DS");
 	  check(_first[l+1]>w,"GEBASZ: CORRUPT DS");
 	}
+      for(int l=0;l<=_max_level;++l) 
+	{
+	  check(_first[l]<=_last_active[l]+1,"GEBASZ: CORRUPT DS");
+	  check(_last_active[l]<_first[l+1],"GEBASZ: CORRUPT DS");
+	  check(_first[l]<=_first[l+1],"GEBASZ: CORRUPT DS");
+	}
       check(_highest_active<0 ||
 	    _first[_highest_active]<=_last_active[_highest_active],
 	    "GEBASZ: CORRUPT DS");
@@ -151,7 +157,6 @@
     void deactivate(Item i)  
     {
       swap(_where[i],_last_active[_level[i]]--);
-      _last_active[_level[i]]--;
       while(_highest_active>=0 &&
 	    _last_active[_highest_active]<_first[_highest_active])
 	_highest_active--;
@@ -175,12 +180,17 @@
     }
 
     ///Return the number of items on level \c l.
-    int &onLevel(int l)
+    int onLevel(int l) const
     {
       return _first[l+1]-_first[l];
     }
+    ///Return the number of items above level \c l.
+    int aboveLevel(int l) const
+    {
+      return _first[_max_level+1]-_first[l+1];
+    }
     ///Return the number of active items on level \c l.
-    int &activesOnLevel(int l)
+    int activesOnLevel(int l) const
     {
       return _last_active[l]-_first[l]+1;
     }
@@ -233,6 +243,8 @@
 
     ///Lift the item returned by highestActive() to level \c new_level.
     ///
+    ///\warning \c new_level must be strictly higher
+    ///than the current level.
     ///
     void liftHighestActiveTo(int new_level) 
     {
@@ -246,11 +258,73 @@
 	}
       copy(li,_first[new_level]);
       _level[li]=new_level;
-	  _highest_active=new_level;
+      _highest_active=new_level;
     }
     
     ///@}
     
+    ///Lift an active item to a higher level.
+
+    ///Lift an active item to a higher level.
+    ///\params i The item to be lifted. It must be active.
+    ///\params new_level The new level of \c i. It must be strictly higher
+    ///than the current level.
+    ///
+    void liftTo(Item i, int new_level) 
+    {
+      const int lo = _level[i];
+      const Vit w = _where[i];
+
+      copy(_last_active[lo],w);
+      copy(--_first[lo+1],_last_active[lo]--);
+      for(int l=lo+1;l<new_level;l++)
+	{
+	  copy(_last_active[l],_first[l]);
+	  copy(--_first[l+1],_last_active[l]--);
+	}
+      copy(i,_first[new_level]);
+      _level[i]=new_level;
+      if(new_level>_highest_active) _highest_active=new_level;
+    }
+
+//     void liftToTop(int l) 
+//     {
+//       const Vit f=_first[l];
+//       for(int i=l;i<=_max_level;i++)
+// 	{
+// 	  _first[i]=f;
+// 	  _last_active[i]=f-1;
+// 	}
+//       for(Vit i=f;i!=_items.end();++i)
+// 	_level[*i]=_max_level;
+//       for(_highest_active=l-1;
+// 	  _highest_active>=0 &&
+// 	    _last_active[_highest_active]<_first[_highest_active];
+// 	  _highest_active--) ;
+//     }
+    
+    ///Lift all nodes on and above a level to the top (and deactivate them).
+
+    ///This function lifts all nodes on and above level \c l to \c maxLevel(),
+    ///and
+    ///also deactivates them.
+    void liftToTop(int l) 
+    {
+      const Vit f=_first[l];
+      const Vit tl=_first[_max_level];
+      for(Vit i=f;i!=tl;++i)
+	_level[*i]=_max_level;
+      for(int i=l;i<=_max_level;i++)
+	{
+	  _first[i]=f;
+	  _last_active[i]=f-1;
+	}
+      for(_highest_active=l-1;
+	  _highest_active>=0 &&
+	    _last_active[_highest_active]<_first[_highest_active];
+	  _highest_active--) ;
+    }
+    
   private:
     int _init_lev;
     Vit _init_num;
@@ -265,10 +339,10 @@
     ///items should be listed levels by levels statring with the lowest one
     ///(with level 0). This is done by using \c initAddItem()
     ///and \c initNewLevel(). Finally \c initFinish() must be called.
-    ///The items not listes will be put on the highest level.
+    ///The items not listed will be put on the highest level.
     ///@{
 
-    ///Starts the initialization process.
+    ///Start the initialization process.
 
     void initStart() 
     {
@@ -306,7 +380,7 @@
       _last_active[_init_lev]=_init_num-1;
     }
 
-    ///Finalizes the initialization process.
+    ///Finalize the initialization process.
 
     void initFinish()
     {