bidirectionalIterator.h

Go to the documentation of this file.
00001 // -*- Mode: C++; tab-width: 2; -*-
00002 // vi: set ts=2:
00003 //
00004 // $Id: bidirectionalIterator.h,v 1.32 2004/02/23 15:19:56 anhi Exp $ 
00005 //
00006 
00007 #ifndef BALL_CONCEPT_BIDIRECTIONALITERATOR_H
00008 #define BALL_CONCEPT_BIDIRECTIONALITERATOR_H
00009 
00010 #ifndef BALL_CONCEPT_FORWARDITERATOR_H
00011 # include <BALL/CONCEPT/forwardIterator.h>
00012 #endif
00013 
00014 namespace BALL 
00015 {
00016 
00021 
00024   template <typename Container, typename DataType, typename Position, typename Traits>
00025   class ConstBidirectionalIterator
00026     : public ConstForwardIterator<Container, DataType, Position, Traits>
00027   {
00028     public:
00029 
00033 
00035     typedef std::bidirectional_iterator_tag iterator_category;
00036     // convenience typedef
00037     typedef ConstForwardIterator<Container, DataType, Position, Traits> Base;   
00039 
00043 
00045     BALL_INLINE ConstBidirectionalIterator()  {}
00046   
00048     BALL_INLINE ConstBidirectionalIterator(const ConstBidirectionalIterator& iterator) 
00049       : Base(iterator)
00050     {
00051     }
00052 
00054     BALL_INLINE ~ConstBidirectionalIterator()  {}
00056 
00060 
00062     BALL_INLINE void toBegin() throw(Exception::Precondition);
00063 
00065     BALL_INLINE bool isBegin() const  { return Base::getTraits().isBegin(); }
00066 
00068     void toEnd() throw(Exception::Precondition);
00069 
00071     BALL_INLINE bool isEnd() const  { return Base::getTraits().isEnd(); }
00072 
00074     void toRBegin() throw(Exception::Precondition);
00075 
00077     BALL_INLINE bool isRBegin() const  { return Base::getTraits().isRBegin(); }
00078 
00080     void toREnd() throw(Exception::Precondition);
00081 
00083     BALL_INLINE bool isREnd() const  { return Base::getTraits().isREnd(); }
00084 
00086     BALL_INLINE ConstBidirectionalIterator& operator ++ () throw(Exception::Precondition);
00087 
00089     BALL_INLINE ConstBidirectionalIterator operator ++ (int) throw(Exception::Precondition);
00090 
00092     BALL_INLINE ConstBidirectionalIterator& operator -- () throw(Exception::Precondition);
00093 
00095     BALL_INLINE ConstBidirectionalIterator operator -- (int) throw(Exception::Precondition);
00096 
00098     static ConstBidirectionalIterator begin(const Container& container) throw(Exception::Precondition);
00099 
00101     static ConstBidirectionalIterator end(const Container& container) throw(Exception::Precondition);
00102 
00104     static ConstBidirectionalIterator rbegin(const Container& container) throw(Exception::Precondition);
00105 
00107     static ConstBidirectionalIterator rend(const Container& container) throw(Exception::Precondition);
00109 
00110     protected:
00111 
00113     BALL_INLINE ConstBidirectionalIterator(const Container& container) 
00114       : Base(container)
00115     {
00116     }
00117   };
00119 
00120   template <typename Container, typename DataType, typename Position, typename Traits>
00121   BALL_INLINE
00122   void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toBegin()
00123     throw(Exception::Precondition)
00124   {
00125     BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to begin")
00126     Base::getTraits().toBegin();
00127   }
00128 
00129   template <typename Container, typename DataType, typename Position, typename Traits>
00130   BALL_INLINE
00131   void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toEnd()
00132     throw(Exception::Precondition)
00133   {
00134     BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to end")
00135     Base::getTraits().toEnd();
00136   }
00137 
00138   template <typename Container, typename DataType, typename Position, typename Traits>
00139   BALL_INLINE
00140   void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toRBegin()
00141     throw(Exception::Precondition)
00142   {
00143     BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to reverse begin")
00144     Base::getTraits().toRBegin();
00145   }
00146 
00147   template <typename Container, typename DataType, typename Position, typename Traits>
00148   BALL_INLINE
00149   void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toREnd()
00150     throw(Exception::Precondition)
00151   { 
00152     BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to reverse end")
00153     Base::getTraits().toREnd();
00154   }
00155 
00156   template <typename Container, typename DataType, typename Position, typename Traits>
00157   BALL_INLINE
00158   ConstBidirectionalIterator<Container, DataType, Position, Traits>& 
00159     ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator ++ ()
00160     throw(Exception::Precondition)
00161   {
00162     BALL_PRECONDITION_EXCEPTION(Base::getTraits().isValid(), "cannot increment an invalid iterator")
00163     Base::getTraits().forward();
00164     return *this;
00165   }
00166 
00167   template <typename Container, typename DataType, typename Position, typename Traits>
00168   BALL_INLINE
00169   ConstBidirectionalIterator<Container, DataType, Position, Traits> 
00170     ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator ++ (int)
00171     throw(Exception::Precondition)
00172   {
00173     BALL_PRECONDITION_EXCEPTION(Base::getTraits().isValid(), "cannot increment an invalid iterator")
00174     ConstBidirectionalIterator iterator(*this);
00175     ++(*this);
00176     return iterator;
00177   }
00178 
00179   template <typename Container, typename DataType, typename Position, typename Traits>
00180   BALL_INLINE
00181   ConstBidirectionalIterator<Container, DataType, Position, Traits>& 
00182     ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator -- ()
00183     throw(Exception::Precondition)
00184   {
00185     BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot decrement unbound iterator")
00186     Base::getTraits().backward();
00187     return *this;
00188   }
00189 
00190   template <typename Container, typename DataType, typename Position, typename Traits>
00191   BALL_INLINE
00192   ConstBidirectionalIterator<Container, DataType, Position, Traits> 
00193     ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator -- (int)
00194     throw(Exception::Precondition)
00195   {
00196     BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot decrement an unbound iterator")
00197     ConstBidirectionalIterator iterator(*this);
00198     --(*this);
00199     return iterator;
00200   }
00201 
00202   template <typename Container, typename DataType, typename Position, typename Traits>
00203   BALL_INLINE
00204   ConstBidirectionalIterator<Container, DataType, Position, Traits> 
00205     ConstBidirectionalIterator<Container, DataType, Position, Traits>::begin(const Container& container)
00206     throw(Exception::Precondition)
00207   {
00208     ConstBidirectionalIterator iterator(container);
00209     iterator.toBegin();
00210     return iterator;
00211   }
00212 
00213   template <typename Container, typename DataType, typename Position, typename Traits>
00214   BALL_INLINE
00215   ConstBidirectionalIterator<Container, DataType, Position, Traits> 
00216     ConstBidirectionalIterator<Container, DataType, Position, Traits>::end(const Container& container)
00217     throw(Exception::Precondition)
00218   {
00219     ConstBidirectionalIterator iterator(container);
00220     iterator.toEnd();
00221     return iterator;
00222   }
00223 
00224   template <typename Container, typename DataType, typename Position, typename Traits>
00225   BALL_INLINE
00226   ConstBidirectionalIterator<Container, DataType, Position, Traits> 
00227     ConstBidirectionalIterator<Container, DataType, Position, Traits>::rbegin(const Container& container)
00228     throw(Exception::Precondition)
00229   {
00230     ConstBidirectionalIterator iterator(container);
00231     iterator.toRBegin();
00232     return iterator;
00233   }
00234 
00235   template <typename Container, typename DataType, typename Position, typename Traits>
00236   BALL_INLINE
00237   ConstBidirectionalIterator<Container, DataType, Position, Traits> 
00238     ConstBidirectionalIterator<Container, DataType, Position, Traits>::rend(const Container& container)
00239     throw(Exception::Precondition)
00240   {
00241     ConstBidirectionalIterator iterator(container);
00242     iterator.toREnd();
00243     return iterator;
00244   }
00245 
00247   template <typename Container, typename DataType, typename Position, typename Traits>
00248   class BidirectionalIterator
00249     : public ConstBidirectionalIterator<Container, DataType, Position, Traits>
00250   {
00251     public:
00252 
00256     
00258     typedef DataType& reference;
00260     typedef DataType* pointer;
00261     // convenience typedef
00262     typedef ConstBidirectionalIterator<Container, DataType, Position, Traits> Base;
00264 
00268 
00270     BALL_INLINE BidirectionalIterator()  {}
00271   
00273     BALL_INLINE BidirectionalIterator(const BidirectionalIterator& iterator)
00274       
00275       : ConstBidirectionalIterator<Container, DataType, Position, Traits>(iterator)
00276     {
00277     }
00278 
00280     BALL_INLINE ~BidirectionalIterator()  {}
00281 
00283 
00287 
00289     BALL_INLINE reference operator * () const  { return (reference)Base::getTraits().getData(); }
00290 
00292     BALL_INLINE pointer operator -> () const  { return (pointer)&Base::getTraits().getData(); }
00293 
00295     BALL_INLINE BidirectionalIterator& operator ++ () throw(Exception::Precondition);
00296 
00298     BALL_INLINE BidirectionalIterator operator ++ (int) throw(Exception::Precondition);
00299 
00301     BALL_INLINE BidirectionalIterator& operator -- () throw(Exception::Precondition);
00302 
00304     BALL_INLINE BidirectionalIterator operator -- (int) throw(Exception::Precondition);
00305 
00307     static BidirectionalIterator begin(const Container& container)
00308       throw(Exception::Precondition);
00309 
00311     static BidirectionalIterator end(const Container& container)
00312       throw(Exception::Precondition);
00313 
00315     static BidirectionalIterator rbegin(const Container& container)
00316       throw(Exception::Precondition);
00317 
00319     static BidirectionalIterator rend(const Container& container)
00320       throw(Exception::Precondition);
00322 
00323     protected:
00324 
00326     BALL_INLINE BidirectionalIterator(const Container& container) ;
00327   };
00328 
00329 
00330   template <typename Container, typename DataType, typename Position, typename Traits>
00331   BALL_INLINE
00332   BidirectionalIterator<Container, DataType, Position, Traits>& 
00333     BidirectionalIterator<Container, DataType, Position, Traits>::operator ++ ()
00334     throw(Exception::Precondition)
00335   {
00336     Base::operator ++ ();
00337     return *this;
00338   }
00339 
00340   template <typename Container, typename DataType, typename Position, typename Traits>
00341   BALL_INLINE
00342   BidirectionalIterator<Container, DataType, Position, Traits> 
00343     BidirectionalIterator<Container, DataType, Position, Traits>::operator ++ (int)
00344     throw(Exception::Precondition)
00345   {
00346     BidirectionalIterator iterator(*this);
00347     this->operator ++ ();
00348     return iterator;
00349   }
00350 
00351   template <typename Container, typename DataType, typename Position, typename Traits>
00352   BALL_INLINE
00353   BidirectionalIterator<Container, DataType, Position, Traits>& 
00354     BidirectionalIterator<Container, DataType, Position, Traits>::operator -- ()
00355     throw(Exception::Precondition)
00356   {
00357     Base::operator -- ();
00358     return *this;
00359   }
00360 
00361   template <typename Container, typename DataType, typename Position, typename Traits>
00362   BALL_INLINE
00363   BidirectionalIterator<Container, DataType, Position, Traits> 
00364     BidirectionalIterator<Container, DataType, Position, Traits>::operator -- (int)
00365     throw(Exception::Precondition)
00366   {
00367     BidirectionalIterator iterator(*this);
00368     this->operator -- ();
00369     return iterator;
00370   }
00371 
00372   template <typename Container, typename DataType, typename Position, typename Traits>
00373   BALL_INLINE
00374   BidirectionalIterator<Container, DataType, Position, Traits> 
00375     BidirectionalIterator<Container, DataType, Position, Traits>::begin(const Container& container)
00376     throw(Exception::Precondition)
00377   {
00378     BidirectionalIterator iterator(container);
00379     iterator.toBegin();
00380     return iterator;
00381   }
00382 
00383   template <typename Container, typename DataType, typename Position, typename Traits>
00384   BALL_INLINE
00385   BidirectionalIterator<Container, DataType, Position, Traits>
00386     BidirectionalIterator<Container, DataType, Position, Traits>::end(const Container& container)
00387     throw(Exception::Precondition)
00388   {
00389     BidirectionalIterator iterator(container);
00390     iterator.toEnd();
00391     return iterator;
00392   }
00393 
00394   template <typename Container, typename DataType, typename Position, typename Traits>
00395   BALL_INLINE
00396   BidirectionalIterator<Container, DataType, Position, Traits> 
00397     BidirectionalIterator<Container, DataType, Position, Traits>::rbegin(const Container& container)
00398     throw(Exception::Precondition)
00399   {
00400     BidirectionalIterator iterator(container);
00401     iterator.toRBegin();
00402     return iterator;
00403   }
00404 
00405   template <typename Container, typename DataType, typename Position, typename Traits>
00406   BALL_INLINE
00407   BidirectionalIterator<Container, DataType, Position, Traits> 
00408     BidirectionalIterator<Container, DataType, Position, Traits>::rend(const Container& container)
00409     throw(Exception::Precondition)
00410   {
00411     BidirectionalIterator iterator(container);
00412     iterator.toREnd();
00413     return iterator;
00414   }
00415 
00416   template <typename Container, typename DataType, typename Position, typename Traits>
00417   BALL_INLINE
00418   BidirectionalIterator<Container, DataType, Position, Traits>::BidirectionalIterator(const Container& container)
00419     
00420     : ConstBidirectionalIterator<Container, DataType, Position, Traits>(container)
00421   {
00422   }
00423 
00424 
00425 } // namespace BALL 
00426 
00427 #endif // BALL_CONCEPT_BIDIRECTIONALITERATOR_H