00001
00002
00003
00004
00005 #ifndef BALL_CONCEPT_BIDIRECTIONALITERATOR_H
00006 #define BALL_CONCEPT_BIDIRECTIONALITERATOR_H
00007
00008 #ifndef BALL_CONCEPT_FORWARDITERATOR_H
00009 # include <BALL/CONCEPT/forwardIterator.h>
00010 #endif
00011
00012 namespace BALL
00013 {
00014
00019
00022 template <typename Container, typename DataType, typename Position, typename Traits>
00023 class ConstBidirectionalIterator
00024 : public ConstForwardIterator<Container, DataType, Position, Traits>
00025 {
00026 public:
00027
00031
00033 typedef std::bidirectional_iterator_tag iterator_category;
00034
00035 typedef ConstForwardIterator<Container, DataType, Position, Traits> Base;
00037
00041
00043 BALL_INLINE ConstBidirectionalIterator() {}
00044
00046 BALL_INLINE ConstBidirectionalIterator(const ConstBidirectionalIterator& iterator)
00047 : Base(iterator)
00048 {
00049 }
00050
00052 BALL_INLINE ~ConstBidirectionalIterator() {}
00054
00058
00060 BALL_INLINE void toBegin() throw(Exception::Precondition);
00061
00063 BALL_INLINE bool isBegin() const { return Base::getTraits().isBegin(); }
00064
00066 void toEnd() throw(Exception::Precondition);
00067
00069 BALL_INLINE bool isEnd() const { return Base::getTraits().isEnd(); }
00070
00072 void toRBegin() throw(Exception::Precondition);
00073
00075 BALL_INLINE bool isRBegin() const { return Base::getTraits().isRBegin(); }
00076
00078 void toREnd() throw(Exception::Precondition);
00079
00081 BALL_INLINE bool isREnd() const { return Base::getTraits().isREnd(); }
00082
00084 BALL_INLINE ConstBidirectionalIterator& operator ++ () throw(Exception::Precondition);
00085
00087 BALL_INLINE ConstBidirectionalIterator operator ++ (int) throw(Exception::Precondition);
00088
00090 BALL_INLINE ConstBidirectionalIterator& operator -- () throw(Exception::Precondition);
00091
00093 BALL_INLINE ConstBidirectionalIterator operator -- (int) throw(Exception::Precondition);
00094
00096 static ConstBidirectionalIterator begin(const Container& container) throw(Exception::Precondition);
00097
00099 static ConstBidirectionalIterator end(const Container& container) throw(Exception::Precondition);
00100
00102 static ConstBidirectionalIterator rbegin(const Container& container) throw(Exception::Precondition);
00103
00105 static ConstBidirectionalIterator rend(const Container& container) throw(Exception::Precondition);
00107
00108 protected:
00109
00111 BALL_INLINE ConstBidirectionalIterator(const Container& container)
00112 : Base(container)
00113 {
00114 }
00115 };
00117
00118 template <typename Container, typename DataType, typename Position, typename Traits>
00119 BALL_INLINE
00120 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toBegin()
00121 throw(Exception::Precondition)
00122 {
00123 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to begin")
00124 Base::getTraits().toBegin();
00125 }
00126
00127 template <typename Container, typename DataType, typename Position, typename Traits>
00128 BALL_INLINE
00129 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toEnd()
00130 throw(Exception::Precondition)
00131 {
00132 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to end")
00133 Base::getTraits().toEnd();
00134 }
00135
00136 template <typename Container, typename DataType, typename Position, typename Traits>
00137 BALL_INLINE
00138 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toRBegin()
00139 throw(Exception::Precondition)
00140 {
00141 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to reverse begin")
00142 Base::getTraits().toRBegin();
00143 }
00144
00145 template <typename Container, typename DataType, typename Position, typename Traits>
00146 BALL_INLINE
00147 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toREnd()
00148 throw(Exception::Precondition)
00149 {
00150 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to reverse end")
00151 Base::getTraits().toREnd();
00152 }
00153
00154 template <typename Container, typename DataType, typename Position, typename Traits>
00155 BALL_INLINE
00156 ConstBidirectionalIterator<Container, DataType, Position, Traits>&
00157 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator ++ ()
00158 throw(Exception::Precondition)
00159 {
00160 BALL_PRECONDITION_EXCEPTION(Base::getTraits().isValid(), "cannot increment an invalid iterator")
00161 Base::getTraits().forward();
00162 return *this;
00163 }
00164
00165 template <typename Container, typename DataType, typename Position, typename Traits>
00166 BALL_INLINE
00167 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00168 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator ++ (int)
00169 throw(Exception::Precondition)
00170 {
00171 BALL_PRECONDITION_EXCEPTION(Base::getTraits().isValid(), "cannot increment an invalid iterator")
00172 ConstBidirectionalIterator iterator(*this);
00173 ++(*this);
00174 return iterator;
00175 }
00176
00177 template <typename Container, typename DataType, typename Position, typename Traits>
00178 BALL_INLINE
00179 ConstBidirectionalIterator<Container, DataType, Position, Traits>&
00180 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator -- ()
00181 throw(Exception::Precondition)
00182 {
00183 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot decrement unbound iterator")
00184 Base::getTraits().backward();
00185 return *this;
00186 }
00187
00188 template <typename Container, typename DataType, typename Position, typename Traits>
00189 BALL_INLINE
00190 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00191 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator -- (int)
00192 throw(Exception::Precondition)
00193 {
00194 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot decrement an unbound iterator")
00195 ConstBidirectionalIterator iterator(*this);
00196 --(*this);
00197 return iterator;
00198 }
00199
00200 template <typename Container, typename DataType, typename Position, typename Traits>
00201 BALL_INLINE
00202 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00203 ConstBidirectionalIterator<Container, DataType, Position, Traits>::begin(const Container& container)
00204 throw(Exception::Precondition)
00205 {
00206 ConstBidirectionalIterator iterator(container);
00207 iterator.toBegin();
00208 return iterator;
00209 }
00210
00211 template <typename Container, typename DataType, typename Position, typename Traits>
00212 BALL_INLINE
00213 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00214 ConstBidirectionalIterator<Container, DataType, Position, Traits>::end(const Container& container)
00215 throw(Exception::Precondition)
00216 {
00217 ConstBidirectionalIterator iterator(container);
00218 iterator.toEnd();
00219 return iterator;
00220 }
00221
00222 template <typename Container, typename DataType, typename Position, typename Traits>
00223 BALL_INLINE
00224 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00225 ConstBidirectionalIterator<Container, DataType, Position, Traits>::rbegin(const Container& container)
00226 throw(Exception::Precondition)
00227 {
00228 ConstBidirectionalIterator iterator(container);
00229 iterator.toRBegin();
00230 return iterator;
00231 }
00232
00233 template <typename Container, typename DataType, typename Position, typename Traits>
00234 BALL_INLINE
00235 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00236 ConstBidirectionalIterator<Container, DataType, Position, Traits>::rend(const Container& container)
00237 throw(Exception::Precondition)
00238 {
00239 ConstBidirectionalIterator iterator(container);
00240 iterator.toREnd();
00241 return iterator;
00242 }
00243
00245 template <typename Container, typename DataType, typename Position, typename Traits>
00246 class BidirectionalIterator
00247 : public ConstBidirectionalIterator<Container, DataType, Position, Traits>
00248 {
00249 public:
00250
00254
00256 typedef DataType& reference;
00258 typedef DataType* pointer;
00259
00260 typedef ConstBidirectionalIterator<Container, DataType, Position, Traits> Base;
00262
00266
00268 BALL_INLINE BidirectionalIterator() {}
00269
00271 BALL_INLINE BidirectionalIterator(const BidirectionalIterator& iterator)
00272
00273 : ConstBidirectionalIterator<Container, DataType, Position, Traits>(iterator)
00274 {
00275 }
00276
00278 BALL_INLINE ~BidirectionalIterator() {}
00279
00281
00285
00287 BALL_INLINE reference operator * () const { return (reference)Base::getTraits().getData(); }
00288
00290 BALL_INLINE pointer operator -> () const { return (pointer)&Base::getTraits().getData(); }
00291
00293 BALL_INLINE BidirectionalIterator& operator ++ () throw(Exception::Precondition);
00294
00296 BALL_INLINE BidirectionalIterator operator ++ (int) throw(Exception::Precondition);
00297
00299 BALL_INLINE BidirectionalIterator& operator -- () throw(Exception::Precondition);
00300
00302 BALL_INLINE BidirectionalIterator operator -- (int) throw(Exception::Precondition);
00303
00305 static BidirectionalIterator begin(const Container& container)
00306 throw(Exception::Precondition);
00307
00309 static BidirectionalIterator end(const Container& container)
00310 throw(Exception::Precondition);
00311
00313 static BidirectionalIterator rbegin(const Container& container)
00314 throw(Exception::Precondition);
00315
00317 static BidirectionalIterator rend(const Container& container)
00318 throw(Exception::Precondition);
00320
00321 protected:
00322
00324 BALL_INLINE BidirectionalIterator(const Container& container) ;
00325 };
00326
00327
00328 template <typename Container, typename DataType, typename Position, typename Traits>
00329 BALL_INLINE
00330 BidirectionalIterator<Container, DataType, Position, Traits>&
00331 BidirectionalIterator<Container, DataType, Position, Traits>::operator ++ ()
00332 throw(Exception::Precondition)
00333 {
00334 Base::operator ++ ();
00335 return *this;
00336 }
00337
00338 template <typename Container, typename DataType, typename Position, typename Traits>
00339 BALL_INLINE
00340 BidirectionalIterator<Container, DataType, Position, Traits>
00341 BidirectionalIterator<Container, DataType, Position, Traits>::operator ++ (int)
00342 throw(Exception::Precondition)
00343 {
00344 BidirectionalIterator iterator(*this);
00345 this->operator ++ ();
00346 return iterator;
00347 }
00348
00349 template <typename Container, typename DataType, typename Position, typename Traits>
00350 BALL_INLINE
00351 BidirectionalIterator<Container, DataType, Position, Traits>&
00352 BidirectionalIterator<Container, DataType, Position, Traits>::operator -- ()
00353 throw(Exception::Precondition)
00354 {
00355 Base::operator -- ();
00356 return *this;
00357 }
00358
00359 template <typename Container, typename DataType, typename Position, typename Traits>
00360 BALL_INLINE
00361 BidirectionalIterator<Container, DataType, Position, Traits>
00362 BidirectionalIterator<Container, DataType, Position, Traits>::operator -- (int)
00363 throw(Exception::Precondition)
00364 {
00365 BidirectionalIterator iterator(*this);
00366 this->operator -- ();
00367 return iterator;
00368 }
00369
00370 template <typename Container, typename DataType, typename Position, typename Traits>
00371 BALL_INLINE
00372 BidirectionalIterator<Container, DataType, Position, Traits>
00373 BidirectionalIterator<Container, DataType, Position, Traits>::begin(const Container& container)
00374 throw(Exception::Precondition)
00375 {
00376 BidirectionalIterator iterator(container);
00377 iterator.toBegin();
00378 return iterator;
00379 }
00380
00381 template <typename Container, typename DataType, typename Position, typename Traits>
00382 BALL_INLINE
00383 BidirectionalIterator<Container, DataType, Position, Traits>
00384 BidirectionalIterator<Container, DataType, Position, Traits>::end(const Container& container)
00385 throw(Exception::Precondition)
00386 {
00387 BidirectionalIterator iterator(container);
00388 iterator.toEnd();
00389 return iterator;
00390 }
00391
00392 template <typename Container, typename DataType, typename Position, typename Traits>
00393 BALL_INLINE
00394 BidirectionalIterator<Container, DataType, Position, Traits>
00395 BidirectionalIterator<Container, DataType, Position, Traits>::rbegin(const Container& container)
00396 throw(Exception::Precondition)
00397 {
00398 BidirectionalIterator iterator(container);
00399 iterator.toRBegin();
00400 return iterator;
00401 }
00402
00403 template <typename Container, typename DataType, typename Position, typename Traits>
00404 BALL_INLINE
00405 BidirectionalIterator<Container, DataType, Position, Traits>
00406 BidirectionalIterator<Container, DataType, Position, Traits>::rend(const Container& container)
00407 throw(Exception::Precondition)
00408 {
00409 BidirectionalIterator iterator(container);
00410 iterator.toREnd();
00411 return iterator;
00412 }
00413
00414 template <typename Container, typename DataType, typename Position, typename Traits>
00415 BALL_INLINE
00416 BidirectionalIterator<Container, DataType, Position, Traits>::BidirectionalIterator(const Container& container)
00417
00418 : ConstBidirectionalIterator<Container, DataType, Position, Traits>(container)
00419 {
00420 }
00421
00422
00423 }
00424
00425 #endif // BALL_CONCEPT_BIDIRECTIONALITERATOR_H