Stxxl  1.4.0
include/stxxl/bits/containers/deque.h
Go to the documentation of this file.
00001 /***************************************************************************
00002  *  include/stxxl/bits/containers/deque.h
00003  *
00004  *  Part of the STXXL. See http://stxxl.sourceforge.net
00005  *
00006  *  Copyright (C) 2006 Roman Dementiev <dementiev@ira.uka.de>
00007  *  Copyright (C) 2008, 2009 Andreas Beckmann <beckmann@cs.uni-frankfurt.de>
00008  *
00009  *  Distributed under the Boost Software License, Version 1.0.
00010  *  (See accompanying file LICENSE_1_0.txt or copy at
00011  *  http://www.boost.org/LICENSE_1_0.txt)
00012  **************************************************************************/
00013 
00014 #ifndef _STXXL_DEQUE_H
00015 #define _STXXL_DEQUE_H
00016 
00017 #include <limits>
00018 #include <stxxl/vector>
00019 
00020 
00021 __STXXL_BEGIN_NAMESPACE
00022 
00023 template <class T, class VectorType>
00024 class deque;
00025 
00026 template <class DequeType>
00027 class const_deque_iterator;
00028 
00029 template <class DequeType>
00030 class deque_iterator
00031 {
00032     typedef typename DequeType::size_type size_type;
00033     typedef typename DequeType::vector_type vector_type;
00034     typedef deque_iterator<DequeType> _Self;
00035     DequeType * Deque;
00036     size_type Offset;
00037 
00038     deque_iterator(DequeType * Deque_, size_type Offset_) :
00039         Deque(Deque_), Offset(Offset_)
00040     { }
00041 
00042     friend class const_deque_iterator<DequeType>;
00043 
00044 public:
00045     typedef typename DequeType::value_type value_type;
00046     typedef typename DequeType::pointer pointer;
00047     typedef typename DequeType::const_pointer const_pointer;
00048     typedef typename DequeType::reference reference;
00049     typedef typename DequeType::const_reference const_reference;
00050     typedef deque_iterator<DequeType> iterator;
00051     typedef const_deque_iterator<DequeType> const_iterator;
00052     friend class deque<value_type, vector_type>;
00053     typedef std::random_access_iterator_tag iterator_category;
00054     typedef typename DequeType::difference_type difference_type;
00055 
00056     deque_iterator() : Deque(NULL), Offset(0) { }
00057 
00058     difference_type operator - (const _Self & a) const
00059     {
00060         size_type SelfAbsOffset = (Offset >= Deque->begin_o) ?
00061                                   Offset : (Deque->Vector.size() + Offset);
00062         size_type aAbsOffset = (a.Offset >= Deque->begin_o) ?
00063                                a.Offset : (Deque->Vector.size() + a.Offset);
00064 
00065         return SelfAbsOffset - aAbsOffset;
00066     }
00067 
00068     difference_type operator - (const const_iterator & a) const
00069     {
00070         size_type SelfAbsOffset = (Offset >= Deque->begin_o) ?
00071                                   Offset : (Deque->Vector.size() + Offset);
00072         size_type aAbsOffset = (a.Offset >= Deque->begin_o) ?
00073                                a.Offset : (Deque->Vector.size() + a.Offset);
00074 
00075         return SelfAbsOffset - aAbsOffset;
00076     }
00077 
00078     _Self operator - (size_type op) const
00079     {
00080         return _Self(Deque, (Offset + Deque->Vector.size() - op) % Deque->Vector.size());
00081     }
00082 
00083     _Self operator + (size_type op) const
00084     {
00085         return _Self(Deque, (Offset + op) % Deque->Vector.size());
00086     }
00087 
00088     _Self & operator -= (size_type op)
00089     {
00090         Offset = (Offset + Deque->Vector.size() - op) % Deque->Vector.size();
00091         return *this;
00092     }
00093 
00094     _Self & operator += (size_type op)
00095     {
00096         Offset = (Offset + op) % Deque->Vector.size();
00097         return *this;
00098     }
00099 
00100     reference operator * ()
00101     {
00102         return Deque->Vector[Offset];
00103     }
00104 
00105     pointer operator -> ()
00106     {
00107         return &(Deque->Vector[Offset]);
00108     }
00109 
00110     const_reference operator * () const
00111     {
00112         return Deque->Vector[Offset];
00113     }
00114 
00115     const_pointer operator -> () const
00116     {
00117         return &(Deque->Vector[Offset]);
00118     }
00119 
00120     reference operator [] (size_type op)
00121     {
00122         return Deque->Vector[(Offset + op) % Deque->Vector.size()];
00123     }
00124 
00125     const_reference operator [] (size_type op) const
00126     {
00127         return Deque->Vector[(Offset + op) % Deque->Vector.size()];
00128     }
00129 
00130     _Self & operator ++ ()
00131     {
00132         Offset = (Offset + 1) % Deque->Vector.size();
00133         return *this;
00134     }
00135     _Self operator ++ (int)
00136     {
00137         _Self __tmp = *this;
00138         Offset = (Offset + 1) % Deque->Vector.size();
00139         return __tmp;
00140     }
00141     _Self & operator -- ()
00142     {
00143         Offset = (Offset + Deque->Vector.size() - 1) % Deque->Vector.size();
00144         return *this;
00145     }
00146     _Self operator -- (int)
00147     {
00148         _Self __tmp = *this;
00149         Offset = (Offset + Deque->Vector.size() - 1) % Deque->Vector.size();
00150         return __tmp;
00151     }
00152     bool operator == (const _Self & a) const
00153     {
00154         assert(Deque == a.Deque);
00155         return Offset == a.Offset;
00156     }
00157     bool operator != (const _Self & a) const
00158     {
00159         assert(Deque == a.Deque);
00160         return Offset != a.Offset;
00161     }
00162 
00163     bool operator < (const _Self & a) const
00164     {
00165         assert(Deque == a.Deque);
00166         return (a - (*this)) > 0;
00167     }
00168 
00169     bool operator > (const _Self & a) const
00170     {
00171         return a < (*this);
00172     }
00173 
00174     bool operator <= (const _Self & a) const
00175     {
00176         return !((*this) > a);
00177     }
00178 
00179     bool operator >= (const _Self & a) const
00180     {
00181         return !((*this) < a);
00182     }
00183 
00184     bool operator == (const const_iterator & a) const
00185     {
00186         assert(Deque == a.Deque);
00187         return Offset == a.Offset;
00188     }
00189     bool operator != (const const_iterator & a) const
00190     {
00191         assert(Deque == a.Deque);
00192         return Offset != a.Offset;
00193     }
00194 
00195     bool operator < (const const_iterator & a) const
00196     {
00197         assert(Deque == a.Deque);
00198         return (a - (*this)) > 0;
00199     }
00200 
00201     bool operator > (const const_iterator & a) const
00202     {
00203         return a < (*this);
00204     }
00205 
00206     bool operator <= (const const_iterator & a) const
00207     {
00208         return !((*this) > a);
00209     }
00210 
00211     bool operator >= (const const_iterator & a) const
00212     {
00213         return !((*this) < a);
00214     }
00215 };
00216 
00217 template <class DequeType>
00218 class const_deque_iterator
00219 {
00220     typedef const_deque_iterator<DequeType> _Self;
00221     typedef typename DequeType::size_type size_type;
00222     typedef typename DequeType::vector_type vector_type;
00223     const DequeType * Deque;
00224     size_type Offset;
00225 
00226     const_deque_iterator(const DequeType * Deque_, size_type Offset_) :
00227         Deque(Deque_), Offset(Offset_)
00228     { }
00229 
00230 public:
00231     typedef typename DequeType::value_type value_type;
00232     typedef typename DequeType::const_pointer pointer;
00233     typedef typename DequeType::const_pointer const_pointer;
00234     typedef typename DequeType::const_reference reference;
00235     typedef typename DequeType::const_reference const_reference;
00236     typedef deque_iterator<DequeType> iterator;
00237     typedef const_deque_iterator<DequeType> const_iterator;
00238     friend class deque<value_type, vector_type>;
00239     friend class deque_iterator<DequeType>;
00240 
00241     typedef std::random_access_iterator_tag iterator_category;
00242     typedef typename DequeType::difference_type difference_type;
00243 
00244     const_deque_iterator() : Deque(NULL), Offset(0) { }
00245     const_deque_iterator(const deque_iterator<DequeType> & it) :
00246         Deque(it.Deque), Offset(it.Offset)
00247     { }
00248 
00249     difference_type operator - (const _Self & a) const
00250     {
00251         size_type SelfAbsOffset = (Offset >= Deque->begin_o) ?
00252                                   Offset : (Deque->Vector.size() + Offset);
00253         size_type aAbsOffset = (a.Offset >= Deque->begin_o) ?
00254                                a.Offset : (Deque->Vector.size() + a.Offset);
00255 
00256         return SelfAbsOffset - aAbsOffset;
00257     }
00258 
00259     difference_type operator - (const iterator & a) const
00260     {
00261         size_type SelfAbsOffset = (Offset >= Deque->begin_o) ?
00262                                   Offset : (Deque->Vector.size() + Offset);
00263         size_type aAbsOffset = (a.Offset >= Deque->begin_o) ?
00264                                a.Offset : (Deque->Vector.size() + a.Offset);
00265 
00266         return SelfAbsOffset - aAbsOffset;
00267     }
00268 
00269     _Self operator - (size_type op) const
00270     {
00271         return _Self(Deque, (Offset + Deque->Vector.size() - op) % Deque->Vector.size());
00272     }
00273 
00274     _Self operator + (size_type op) const
00275     {
00276         return _Self(Deque, (Offset + op) % Deque->Vector.size());
00277     }
00278 
00279     _Self & operator -= (size_type op)
00280     {
00281         Offset = (Offset + Deque->Vector.size() - op) % Deque->Vector.size();
00282         return *this;
00283     }
00284 
00285     _Self & operator += (size_type op)
00286     {
00287         Offset = (Offset + op) % Deque->Vector.size();
00288         return *this;
00289     }
00290 
00291     const_reference operator * () const
00292     {
00293         return Deque->Vector[Offset];
00294     }
00295 
00296     const_pointer operator -> () const
00297     {
00298         return &(Deque->Vector[Offset]);
00299     }
00300 
00301     const_reference operator [] (size_type op) const
00302     {
00303         return Deque->Vector[(Offset + op) % Deque->Vector.size()];
00304     }
00305 
00306     _Self & operator ++ ()
00307     {
00308         Offset = (Offset + 1) % Deque->Vector.size();
00309         return *this;
00310     }
00311     _Self operator ++ (int)
00312     {
00313         _Self __tmp = *this;
00314         Offset = (Offset + 1) % Deque->Vector.size();
00315         return __tmp;
00316     }
00317     _Self & operator -- ()
00318     {
00319         Offset = (Offset + Deque->Vector.size() - 1) % Deque->Vector.size();
00320         return *this;
00321     }
00322     _Self operator -- (int)
00323     {
00324         _Self __tmp = *this;
00325         Offset = (Offset + Deque->Vector.size() - 1) % Deque->Vector.size();
00326         return __tmp;
00327     }
00328     bool operator == (const _Self & a) const
00329     {
00330         assert(Deque == a.Deque);
00331         return Offset == a.Offset;
00332     }
00333     bool operator != (const _Self & a) const
00334     {
00335         assert(Deque == a.Deque);
00336         return Offset != a.Offset;
00337     }
00338 
00339     bool operator < (const _Self & a) const
00340     {
00341         assert(Deque == a.Deque);
00342         return (a - (*this)) > 0;
00343     }
00344 
00345     bool operator > (const _Self & a) const
00346     {
00347         return a < (*this);
00348     }
00349 
00350     bool operator <= (const _Self & a) const
00351     {
00352         return !((*this) > a);
00353     }
00354 
00355     bool operator >= (const _Self & a) const
00356     {
00357         return !((*this) < a);
00358     }
00359 
00360     bool operator == (const iterator & a) const
00361     {
00362         assert(Deque == a.Deque);
00363         return Offset == a.Offset;
00364     }
00365     bool operator != (const iterator & a) const
00366     {
00367         assert(Deque == a.Deque);
00368         return Offset != a.Offset;
00369     }
00370 
00371     bool operator < (const iterator & a) const
00372     {
00373         assert(Deque == a.Deque);
00374         return (a - (*this)) > 0;
00375     }
00376 
00377     bool operator > (const iterator & a) const
00378     {
00379         return a < (*this);
00380     }
00381 
00382     bool operator <= (const iterator & a) const
00383     {
00384         return !((*this) > a);
00385     }
00386 
00387     bool operator >= (const iterator & a) const
00388     {
00389         return !((*this) < a);
00390     }
00391 };
00392 
00393 //! \addtogroup stlcont
00394 //! \{
00395 
00396 //! \brief A deque container
00397 //!
00398 //! It is an adaptor of the \c VectorType.
00399 //! The implementation wraps the elements around
00400 //! the end of the \c VectorType circularly.
00401 //! \tparam T type of the contained objects (POD with no references to internal memory)
00402 //! \tparam VectorType the type of the underlying vector container,
00403 //! the default is \c stxxl::vector<T>
00404 template <class T, class VectorType = stxxl::vector<T> >
00405 class deque : private noncopyable
00406 {
00407     typedef deque<T, VectorType> Self_;
00408 
00409 public:
00410     typedef typename VectorType::size_type size_type;
00411     typedef typename VectorType::difference_type difference_type;
00412     typedef VectorType vector_type;
00413     typedef T value_type;
00414     typedef T * pointer;
00415     typedef const value_type * const_pointer;
00416     typedef T & reference;
00417     typedef const T & const_reference;
00418     typedef deque_iterator<Self_> iterator;
00419     typedef const_deque_iterator<Self_> const_iterator;
00420     typedef std::reverse_iterator<iterator> reverse_iterator;
00421     typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
00422 
00423     friend class deque_iterator<Self_>;
00424     friend class const_deque_iterator<Self_>;
00425 
00426 private:
00427     VectorType Vector;
00428     size_type begin_o, end_o, size_;
00429 
00430     void double_array()
00431     {
00432         const size_type old_size = Vector.size();
00433         Vector.resize(2 * old_size);
00434         if (begin_o > end_o)
00435         {                         // copy data to the new end of the vector
00436             const size_type new_begin_o = old_size + begin_o;
00437             std::copy(Vector.begin() + begin_o,
00438                       Vector.begin() + old_size,
00439                       Vector.begin() + new_begin_o);
00440             begin_o = new_begin_o;
00441         }
00442     }
00443 
00444 public:
00445     deque() : Vector((STXXL_DEFAULT_BLOCK_SIZE(T)) / sizeof(T)), begin_o(0), end_o(0), size_(0)
00446     { }
00447 
00448     deque(size_type n)
00449         : Vector(STXXL_MAX<size_type>(STXXL_DEFAULT_BLOCK_SIZE(T) / sizeof(T), 2 * n)),
00450           begin_o(0), end_o(n), size_(n)
00451     { }
00452 
00453     ~deque()      // empty so far
00454     { }
00455 
00456     iterator begin()
00457     {
00458         return iterator(this, begin_o);
00459     }
00460     iterator end()
00461     {
00462         return iterator(this, end_o);
00463     }
00464     const_iterator begin() const
00465     {
00466         return const_iterator(this, begin_o);
00467     }
00468     const_iterator cbegin() const
00469     {
00470         return begin();
00471     }
00472     const_iterator end() const
00473     {
00474         return const_iterator(this, end_o);
00475     }
00476     const_iterator cend() const
00477     {
00478         return end();
00479     }
00480 
00481     reverse_iterator rbegin()
00482     {
00483         return reverse_iterator(end());
00484     }
00485     const_reverse_iterator rbegin() const
00486     {
00487         return const_reverse_iterator(end());
00488     }
00489     const_reverse_iterator crbegin() const
00490     {
00491         return const_reverse_iterator(end());
00492     }
00493     reverse_iterator rend()
00494     {
00495         return reverse_iterator(begin());
00496     }
00497     const_reverse_iterator rend() const
00498     {
00499         return const_reverse_iterator(begin());
00500     }
00501     const_reverse_iterator crend() const
00502     {
00503         return const_reverse_iterator(begin());
00504     }
00505 
00506     size_type size() const
00507     {
00508         return size_;
00509     }
00510 
00511     size_type max_size() const
00512     {
00513         return (std::numeric_limits<size_type>::max)() / 2 - 1;
00514     }
00515 
00516     bool empty() const
00517     {
00518         return size_ == 0;
00519     }
00520 
00521     reference operator [] (size_type n)
00522     {
00523         assert(n < size());
00524         return Vector[(begin_o + n) % Vector.size()];
00525     }
00526 
00527     const_reference operator [] (size_type n) const
00528     {
00529         assert(n < size());
00530         return Vector[(begin_o + n) % Vector.size()];
00531     }
00532 
00533     reference front()
00534     {
00535         assert(!empty());
00536         return Vector[begin_o];
00537     }
00538 
00539     const_reference front() const
00540     {
00541         assert(!empty());
00542         return Vector[begin_o];
00543     }
00544 
00545     reference back()
00546     {
00547         assert(!empty());
00548         return Vector[(end_o + Vector.size() - 1) % Vector.size()];
00549     }
00550 
00551     const_reference back() const
00552     {
00553         assert(!empty());
00554         return Vector[(end_o + Vector.size() - 1) % Vector.size()];
00555     }
00556 
00557     void push_front(const T & el)
00558     {
00559         if ((begin_o + Vector.size() - 1) % Vector.size() == end_o)
00560         {
00561             // an overflow will occur: resize the array
00562             double_array();
00563         }
00564 
00565         begin_o = (begin_o + Vector.size() - 1) % Vector.size();
00566         Vector[begin_o] = el;
00567         ++size_;
00568     }
00569 
00570     void push_back(const T & el)
00571     {
00572         if ((end_o + 1) % Vector.size() == begin_o)
00573         {
00574             // an overflow will occur: resize the array
00575             double_array();
00576         }
00577         Vector[end_o] = el;
00578         end_o = (end_o + 1) % Vector.size();
00579         ++size_;
00580     }
00581 
00582     void pop_front()
00583     {
00584         assert(!empty());
00585         begin_o = (begin_o + 1) % Vector.size();
00586         --size_;
00587     }
00588 
00589     void pop_back()
00590     {
00591         assert(!empty());
00592         end_o = (end_o + Vector.size() - 1) % Vector.size();
00593         --size_;
00594     }
00595 
00596     void swap(deque & obj)
00597     {
00598         std::swap(Vector, obj.Vector);
00599         std::swap(begin_o, obj.begin_o);
00600         std::swap(end_o, obj.end_o);
00601         std::swap(size_, obj.size_);
00602     }
00603 
00604     void clear()
00605     {
00606         Vector.clear();
00607         Vector.resize((STXXL_DEFAULT_BLOCK_SIZE(T)) / sizeof(T));
00608         begin_o = 0;
00609         end_o = 0;
00610         size_ = 0;
00611     }
00612 
00613     void resize(size_type n)
00614     {
00615         if (n < size())
00616         {
00617             do
00618             {
00619                 pop_back();
00620             } while (n < size());
00621         }
00622         else
00623         {
00624             if (n + 1 > Vector.size())
00625             {                             // need to resize
00626                 const size_type old_size = Vector.size();
00627                 Vector.resize(2 * n);
00628                 if (begin_o > end_o)
00629                 {                         // copy data to the new end of the vector
00630                     const size_type new_begin_o = Vector.size() - old_size + begin_o;
00631                     std::copy(Vector.begin() + begin_o,
00632                               Vector.begin() + old_size,
00633                               Vector.begin() + new_begin_o);
00634                     begin_o = new_begin_o;
00635                 }
00636             }
00637             end_o = (end_o + n - size()) % Vector.size();
00638             size_ = n;
00639         }
00640     }
00641 };
00642 
00643 template <class T, class VectorType>
00644 bool operator == (const deque<T, VectorType> & a, const deque<T, VectorType> & b)
00645 {
00646     return std::equal(a.begin(), a.end(), b.begin());
00647 }
00648 
00649 template <class T, class VectorType>
00650 bool operator < (const deque<T, VectorType> & a, const deque<T, VectorType> & b)
00651 {
00652     return std::lexicographical_compare(a.begin(), a.end(), b.begin(), b.end());
00653 }
00654 
00655 //! \}
00656 
00657 __STXXL_END_NAMESPACE
00658 
00659 namespace std
00660 {
00661     template <typename T, typename VT>
00662     void swap(stxxl::deque<T, VT> & a,
00663               stxxl::deque<T, VT> & b)
00664     {
00665         a.swap(b);
00666     }
00667 }
00668 
00669 #endif /* _STXXL_DEQUE_H */
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines