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
00062 BALL_INLINE void toBegin();
00063
00065 BALL_INLINE bool isBegin() const { return Base::getTraits().isBegin(); }
00066
00070 void toEnd();
00071
00073 BALL_INLINE bool isEnd() const { return Base::getTraits().isEnd(); }
00074
00078 void toRBegin();
00079
00081 BALL_INLINE bool isRBegin() const { return Base::getTraits().isRBegin(); }
00082
00086 void toREnd();
00087
00089 BALL_INLINE bool isREnd() const { return Base::getTraits().isREnd(); }
00090
00094 BALL_INLINE ConstBidirectionalIterator& operator ++ ();
00095
00099 BALL_INLINE ConstBidirectionalIterator operator ++ (int);
00100
00104 BALL_INLINE ConstBidirectionalIterator& operator -- ();
00105
00109 BALL_INLINE ConstBidirectionalIterator operator -- (int);
00110
00114 static ConstBidirectionalIterator begin(const Container& container);
00115
00119 static ConstBidirectionalIterator end(const Container& container);
00120
00124 static ConstBidirectionalIterator rbegin(const Container& container);
00125
00129 static ConstBidirectionalIterator rend(const Container& container);
00131
00132 protected:
00133
00135 BALL_INLINE ConstBidirectionalIterator(const Container& container)
00136 : Base(container)
00137 {
00138 }
00139 };
00141
00142 template <typename Container, typename DataType, typename Position, typename Traits>
00143 BALL_INLINE
00144 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toBegin()
00145 {
00146 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to begin")
00147 Base::getTraits().toBegin();
00148 }
00149
00150 template <typename Container, typename DataType, typename Position, typename Traits>
00151 BALL_INLINE
00152 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toEnd()
00153 {
00154 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to end")
00155 Base::getTraits().toEnd();
00156 }
00157
00158 template <typename Container, typename DataType, typename Position, typename Traits>
00159 BALL_INLINE
00160 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toRBegin()
00161 {
00162 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to reverse begin")
00163 Base::getTraits().toRBegin();
00164 }
00165
00166 template <typename Container, typename DataType, typename Position, typename Traits>
00167 BALL_INLINE
00168 void ConstBidirectionalIterator<Container, DataType, Position, Traits>::toREnd()
00169 {
00170 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot set unbound iterator to reverse end")
00171 Base::getTraits().toREnd();
00172 }
00173
00174 template <typename Container, typename DataType, typename Position, typename Traits>
00175 BALL_INLINE
00176 ConstBidirectionalIterator<Container, DataType, Position, Traits>&
00177 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator ++ ()
00178 {
00179 BALL_PRECONDITION_EXCEPTION(Base::getTraits().isValid(), "cannot increment an invalid iterator")
00180 Base::getTraits().forward();
00181 return *this;
00182 }
00183
00184 template <typename Container, typename DataType, typename Position, typename Traits>
00185 BALL_INLINE
00186 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00187 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator ++ (int)
00188 {
00189 BALL_PRECONDITION_EXCEPTION(Base::getTraits().isValid(), "cannot increment an invalid iterator")
00190 ConstBidirectionalIterator iterator(*this);
00191 ++(*this);
00192 return iterator;
00193 }
00194
00195 template <typename Container, typename DataType, typename Position, typename Traits>
00196 BALL_INLINE
00197 ConstBidirectionalIterator<Container, DataType, Position, Traits>&
00198 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator -- ()
00199 {
00200 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot decrement unbound iterator")
00201 Base::getTraits().backward();
00202 return *this;
00203 }
00204
00205 template <typename Container, typename DataType, typename Position, typename Traits>
00206 BALL_INLINE
00207 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00208 ConstBidirectionalIterator<Container, DataType, Position, Traits>::operator -- (int)
00209 {
00210 BALL_PRECONDITION_EXCEPTION(!Base::getTraits().isSingular(), "cannot decrement an unbound iterator")
00211 ConstBidirectionalIterator iterator(*this);
00212 --(*this);
00213 return iterator;
00214 }
00215
00216 template <typename Container, typename DataType, typename Position, typename Traits>
00217 BALL_INLINE
00218 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00219 ConstBidirectionalIterator<Container, DataType, Position, Traits>::begin(const Container& container)
00220 {
00221 ConstBidirectionalIterator iterator(container);
00222 iterator.toBegin();
00223 return iterator;
00224 }
00225
00226 template <typename Container, typename DataType, typename Position, typename Traits>
00227 BALL_INLINE
00228 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00229 ConstBidirectionalIterator<Container, DataType, Position, Traits>::end(const Container& container)
00230 {
00231 ConstBidirectionalIterator iterator(container);
00232 iterator.toEnd();
00233 return iterator;
00234 }
00235
00236 template <typename Container, typename DataType, typename Position, typename Traits>
00237 BALL_INLINE
00238 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00239 ConstBidirectionalIterator<Container, DataType, Position, Traits>::rbegin(const Container& container)
00240 {
00241 ConstBidirectionalIterator iterator(container);
00242 iterator.toRBegin();
00243 return iterator;
00244 }
00245
00246 template <typename Container, typename DataType, typename Position, typename Traits>
00247 BALL_INLINE
00248 ConstBidirectionalIterator<Container, DataType, Position, Traits>
00249 ConstBidirectionalIterator<Container, DataType, Position, Traits>::rend(const Container& container)
00250 {
00251 ConstBidirectionalIterator iterator(container);
00252 iterator.toREnd();
00253 return iterator;
00254 }
00255
00257 template <typename Container, typename DataType, typename Position, typename Traits>
00258 class BidirectionalIterator
00259 : public ConstBidirectionalIterator<Container, DataType, Position, Traits>
00260 {
00261 public:
00262
00266
00268 typedef DataType& reference;
00270 typedef DataType* pointer;
00271
00272 typedef ConstBidirectionalIterator<Container, DataType, Position, Traits> Base;
00274
00278
00280 BALL_INLINE BidirectionalIterator() {}
00281
00283 BALL_INLINE BidirectionalIterator(const BidirectionalIterator& iterator)
00284
00285 : ConstBidirectionalIterator<Container, DataType, Position, Traits>(iterator)
00286 {
00287 }
00288
00290 BALL_INLINE ~BidirectionalIterator() {}
00291
00293
00297
00299 BALL_INLINE reference operator * () const { return (reference)Base::getTraits().getData(); }
00300
00302 BALL_INLINE pointer operator -> () const { return (pointer)&Base::getTraits().getData(); }
00303
00307 BALL_INLINE BidirectionalIterator& operator ++ ();
00308
00312 BALL_INLINE BidirectionalIterator operator ++ (int);
00313
00317 BALL_INLINE BidirectionalIterator& operator -- ();
00318
00322 BALL_INLINE BidirectionalIterator operator -- (int);
00323
00327 static BidirectionalIterator begin(const Container& container);
00328
00332 static BidirectionalIterator end(const Container& container);
00333
00337 static BidirectionalIterator rbegin(const Container& container);
00338
00342 static BidirectionalIterator rend(const Container& container);
00344
00345 protected:
00346
00348 BALL_INLINE BidirectionalIterator(const Container& container) ;
00349 };
00350
00351
00352 template <typename Container, typename DataType, typename Position, typename Traits>
00353 BALL_INLINE
00354 BidirectionalIterator<Container, DataType, Position, Traits>&
00355 BidirectionalIterator<Container, DataType, Position, Traits>::operator ++ ()
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 {
00366 BidirectionalIterator iterator(*this);
00367 this->operator ++ ();
00368 return iterator;
00369 }
00370
00371 template <typename Container, typename DataType, typename Position, typename Traits>
00372 BALL_INLINE
00373 BidirectionalIterator<Container, DataType, Position, Traits>&
00374 BidirectionalIterator<Container, DataType, Position, Traits>::operator -- ()
00375 {
00376 Base::operator -- ();
00377 return *this;
00378 }
00379
00380 template <typename Container, typename DataType, typename Position, typename Traits>
00381 BALL_INLINE
00382 BidirectionalIterator<Container, DataType, Position, Traits>
00383 BidirectionalIterator<Container, DataType, Position, Traits>::operator -- (int)
00384 {
00385 BidirectionalIterator iterator(*this);
00386 this->operator -- ();
00387 return iterator;
00388 }
00389
00390 template <typename Container, typename DataType, typename Position, typename Traits>
00391 BALL_INLINE
00392 BidirectionalIterator<Container, DataType, Position, Traits>
00393 BidirectionalIterator<Container, DataType, Position, Traits>::begin(const Container& container)
00394 {
00395 BidirectionalIterator iterator(container);
00396 iterator.toBegin();
00397 return iterator;
00398 }
00399
00400 template <typename Container, typename DataType, typename Position, typename Traits>
00401 BALL_INLINE
00402 BidirectionalIterator<Container, DataType, Position, Traits>
00403 BidirectionalIterator<Container, DataType, Position, Traits>::end(const Container& container)
00404 {
00405 BidirectionalIterator iterator(container);
00406 iterator.toEnd();
00407 return iterator;
00408 }
00409
00410 template <typename Container, typename DataType, typename Position, typename Traits>
00411 BALL_INLINE
00412 BidirectionalIterator<Container, DataType, Position, Traits>
00413 BidirectionalIterator<Container, DataType, Position, Traits>::rbegin(const Container& container)
00414 {
00415 BidirectionalIterator iterator(container);
00416 iterator.toRBegin();
00417 return iterator;
00418 }
00419
00420 template <typename Container, typename DataType, typename Position, typename Traits>
00421 BALL_INLINE
00422 BidirectionalIterator<Container, DataType, Position, Traits>
00423 BidirectionalIterator<Container, DataType, Position, Traits>::rend(const Container& container)
00424 {
00425 BidirectionalIterator iterator(container);
00426 iterator.toREnd();
00427 return iterator;
00428 }
00429
00430 template <typename Container, typename DataType, typename Position, typename Traits>
00431 BALL_INLINE
00432 BidirectionalIterator<Container, DataType, Position, Traits>::BidirectionalIterator(const Container& container)
00433
00434 : ConstBidirectionalIterator<Container, DataType, Position, Traits>(container)
00435 {
00436 }
00437
00438
00439 }
00440
00441 #endif // BALL_CONCEPT_BIDIRECTIONALITERATOR_H