// file : odb/vector.hxx // copyright : Copyright (c) 2009-2013 Code Synthesis Tools CC // license : GNU GPL v2; see accompanying LICENSE file #ifndef ODB_VECTOR_HXX #define ODB_VECTOR_HXX #include #include // ODB_CXX11 #include #include #ifdef ODB_CXX11 # include // std::move, std::forward # ifdef ODB_CXX11_INITIALIZER_LIST # include # endif #endif #include namespace odb { // An std::vector-like container that keeps track of changes. // // Note that the style and order of definitions is as appears // in the standard. // template class vector_iterator; template > class vector: public vector_base { public: typedef std::vector base_vector_type; typedef typename base_vector_type::iterator base_iterator_type; typedef typename base_vector_type::reverse_iterator base_reverse_iterator_type; // types: // typedef typename base_vector_type::reference reference; typedef typename base_vector_type::const_reference const_reference; typedef vector_iterator iterator; typedef typename base_vector_type::const_iterator const_iterator; typedef typename base_vector_type::size_type size_type; typedef typename base_vector_type::difference_type difference_type; typedef T value_type; typedef A allocator_type; typedef typename base_vector_type::pointer pointer; typedef typename base_vector_type::const_pointer const_pointer; typedef vector_iterator reverse_iterator; typedef typename base_vector_type::const_reverse_iterator const_reverse_iterator; // construct/copy/destroy: // explicit vector(const A& a = A()): v_ (a) {} explicit vector(size_type n): v_ (n) {} // C++11 vector(size_type n, const T& v, const A& a = A()): v_ (n, v, a) {} template vector(I f, I l, const A& a = A()) : v_ (f, l, a) {} vector(const vector& x): vector_base (x), v_ (x.v_) {} // ~vector() {} vector& operator=(const vector&); template void assign(I f, I l); void assign(size_type n, const T& u); allocator_type get_allocator() const /*noexcept*/ {return v_.get_allocator ();} #ifdef ODB_CXX11 vector(vector&& x): vector_base (std::move (x)), v_ (std::move (x.v_)) {} vector(const vector& x, const A& a): vector_base (x), v_ (x.v_, a) {} vector(vector&& x, const A& a) : vector_base (std::move (x)), v_ (std::move (x.v_), a) {} vector& operator=(vector&&); #ifdef ODB_CXX11_INITIALIZER_LIST vector(std::initializer_list il, const A& a = A()): v_ (il, a) {} vector& operator=(std::initializer_list); void assign(std::initializer_list); #endif #endif // iterators: (all /*noexcept*/) // iterator begin() {return iterator (this, v_.begin ());} const_iterator begin() const {return v_.begin ();} iterator end() {return iterator (this, v_.end ());} const_iterator end() const {return v_.end ();} reverse_iterator rbegin() {return reverse_iterator (this, v_.rbegin ());} const_reverse_iterator rbegin() const {return v_.rbegin ();} reverse_iterator rend() {return reverse_iterator (this, v_.rend ());} const_reverse_iterator rend() const {return v_.rend ();} // Return standard vector iterators. The begin() functions mark all // the elements as modified. // base_iterator_type mbegin (); base_iterator_type mend () {return v_.end ();} base_reverse_iterator_type mrbegin (); base_reverse_iterator_type mrend () {return v_.rend ();} #ifdef ODB_CXX11 const_iterator cbegin() const {return v_.cbegin ();} const_iterator cend() const {return v_.cend ();} const_reverse_iterator crbegin() const {return v_.crbegin ();} const_reverse_iterator crend() const {return v_.crend ();} #endif // capacity: // size_type size() const /*noexcept*/ {return v_.size ();} size_type max_size() const /*noexcept*/ {return v_.max_size ();} void resize(size_type); // C++11 void resize(size_type, const T&); size_type capacity() const /*noexcept*/ {return v_.capacity ();} bool empty() const /*noexcept*/ {return v_.empty ();} void reserve(size_type); #ifdef ODB_CXX11 void shrink_to_fit(); #endif // element access: // //reference operator[](size_type n); reference modify(size_type n); const_reference operator[](size_type n) const {return v_[n];} //reference at(size_type n); reference modify_at(size_type n); const_reference at(size_type n) const {return v_.at (n);} //reference front(); reference modify_front(); const_reference front() const {return v_.front ();} //reference back(); reference modify_back(); const_reference back() const {return v_.back ();} // data access: // #ifdef ODB_CXX11 //T* data() noexcept; T* modify_data() /*noexcept*/; const T* data() const /*noexcept*/ {return v_.data ();} #endif // modifiers: // void push_back(const T& x); void pop_back(); iterator insert(iterator position, const T& x); void insert(iterator position, size_type n, const T& x); template void insert(iterator position, I first, I last); iterator erase(iterator position); iterator erase(iterator first, iterator last); void swap(vector&); void clear() /*noexcept*/; #ifdef ODB_CXX11 // In C++11 all modifiers use const_iterator instead of iterator // to represent position. However, some standard libraries (notably // GCC's) still use iterator and so we will do that as well, for now. // void push_back(T&& x); iterator insert(iterator position, T&& x); #ifdef ODB_CXX11_VARIADIC_TEMPLATE template void emplace_back(Args&&... args); template iterator emplace(iterator position, Args&&... args); #endif #endif // Interfacing with the base vector. // vector (const base_vector_type& x): v_ (x) {} vector& operator= (const base_vector_type&); operator const base_vector_type& () const {return v_;} base_vector_type& base () {return v_;} const base_vector_type& base () const {return v_;} #ifdef ODB_CXX11 vector (base_vector_type&& x): v_ (std::move (x)) {} vector& operator= (base_vector_type&&); #endif // Change tracking (the rest comes from vector_base). // public: void _start () const {impl_.start (v_.size ());} private: base_vector_type v_; }; namespace core { using odb::vector; } template inline bool operator==(const vector& x, const vector& y) {return x.base () == y.base ();} template inline bool operator==(const vector& x, const std::vector& y) {return x.base () == y;} template inline bool operator==(const std::vector& x, const vector& y) {return x == y.base ();} template inline bool operator< (const vector& x, const vector& y) {return x.base () < y.base ();} template inline bool operator<(const vector& x, const std::vector& y) {return x.base () < y;} template inline bool operator<(const std::vector& x, const vector& y) {return x < y.base ();} template inline bool operator!=(const vector& x, const vector& y) {return x.base () != y.base ();} template inline bool operator!=(const vector& x, const std::vector& y) {return x.base () != y;} template inline bool operator!=(const std::vector& x, const vector& y) {return x != y.base ();} template inline bool operator> (const vector& x, const vector& y) {return x.base () > y.base ();} template inline bool operator>=(const vector& x, const vector& y) {return x.base () >= y.base ();} template inline bool operator>=(const vector& x, const std::vector& y) {return x.base () >= y;} template inline bool operator>=(const std::vector& x, const vector& y) {return x >= y.base ();} template inline bool operator<=(const vector& x, const vector& y) {return x.base () <= y.base ();} template inline bool operator<=(const vector& x, const std::vector& y) {return x.base () <= y;} template inline bool operator<=(const std::vector& x, const vector& y) {return x <= y.base ();} template class vector_iterator { public: typedef V vector_type; typedef I base_iterator_type; typedef typename vector_type::const_iterator const_iterator_type; typedef std::iterator_traits base_iterator_traits; typedef typename base_iterator_traits::value_type value_type; typedef typename base_iterator_traits::difference_type difference_type; typedef typename base_iterator_traits::pointer pointer; typedef typename base_iterator_traits::reference reference; typedef typename base_iterator_traits::iterator_category iterator_category; typedef typename vector_type::size_type size_type; typedef typename vector_type::const_reference const_reference; typedef typename vector_type::const_pointer const_pointer; vector_iterator (): v_ (0), i_ () {} vector_iterator (vector_type* v, const base_iterator_type& i) : v_ (v), i_ (i) {} operator const_iterator_type () const {return i_;} base_iterator_type base () const {return i_;} vector_type* vector () const {return v_;} // Note: const_{reference,pointer}. // const_reference operator* () const {return *i_;} const_pointer operator-> () const {return i_.operator -> ();} const_reference operator[] (difference_type n) const {return i_[n];} // Modifiers. // reference modify () const; reference modify (difference_type n) const; vector_iterator& operator++ () {++i_; return *this;} vector_iterator operator++ (int) {return vector_iterator (v_, i_++);} vector_iterator& operator-- () {--i_; return *this;} vector_iterator operator-- (int) {return vector_iterator (v_, i_--);} vector_iterator operator+ (difference_type n) const {return vector_iterator (v_, i_ + n);} vector_iterator& operator+= (difference_type n) {i_ += n; return *this;} vector_iterator operator- (difference_type n) const {return vector_iterator (v_, i_ - n);} vector_iterator& operator-= (difference_type n) {i_ -= n; return *this;} // Implementation details. // public: base_iterator_type _base () const {return i_;} // Same as base (). private: vector_type* v_; base_iterator_type i_; }; template class vector_iterator > { public: typedef V vector_type; typedef std::reverse_iterator base_iterator_type; typedef typename vector_type::const_reverse_iterator const_iterator_type; typedef std::iterator_traits base_iterator_traits; typedef typename vector_type::iterator iterator_type; typedef typename base_iterator_traits::value_type value_type; typedef typename base_iterator_traits::difference_type difference_type; typedef typename base_iterator_traits::pointer pointer; typedef typename base_iterator_traits::reference reference; typedef typename base_iterator_traits::iterator_category iterator_category; typedef typename vector_type::size_type size_type; typedef typename vector_type::const_reference const_reference; typedef typename vector_type::const_pointer const_pointer; vector_iterator (): v_ (0), i_ () {} explicit vector_iterator (const iterator_type& i) : v_ (i.vector ()), i_ (i.base ()) {} vector_iterator (vector_type* v, const base_iterator_type& i) : v_ (v), i_ (i) {} operator const_iterator_type () const {return i_;} iterator_type base () const {return iterator_type (v_, i_.base ());} base_iterator_type rbase () const {return i_;} vector_type* vector () const {return v_;} // Note: const_{reference,pointer}. // const_reference operator* () const {return *i_;} const_pointer operator-> () const {return i_.operator -> ();} const_reference operator[] (difference_type n) const {return i_[n];} // Modifiers. // reference modify () const; reference modify (difference_type n) const; vector_iterator& operator++ () {++i_; return *this;} vector_iterator operator++ (int) {return vector_iterator (v_, i_++);} vector_iterator& operator-- () {--i_; return *this;} vector_iterator operator-- (int) {return vector_iterator (v_, i_--);} vector_iterator operator+ (difference_type n) const {return vector_iterator (v_, i_ + n);} vector_iterator& operator+= (difference_type n) {i_ += n; return *this;} vector_iterator operator- (difference_type n) const {return vector_iterator (v_, i_ - n);} vector_iterator& operator-= (difference_type n) {i_ -= n; return *this;} // Implementation details. // public: base_iterator_type _base () const {return i_;} // Same as rbase(). private: vector_type* v_; base_iterator_type i_; }; // operator== // template inline bool operator== (const vector_iterator& x, const vector_iterator& y) {return x._base () == y._base ();} template inline bool operator== (const vector_iterator& x, const typename vector_iterator::const_iterator_type& y) {return x._base () == y;} template inline bool operator== (const typename vector_iterator::const_iterator_type& x, const vector_iterator& y) {return x == y._base ();} // operator< // template inline bool operator< (const vector_iterator& x, const vector_iterator& y) {return x._base () < y._base ();} template inline bool operator< (const vector_iterator& x, const typename vector_iterator::const_iterator_type& y) {return x._base () < y;} template inline bool operator< (const typename vector_iterator::const_iterator_type& x, const vector_iterator& y) {return x < y._base ();} // operator!= // template inline bool operator!= (const vector_iterator& x, const vector_iterator& y) {return x._base () != y._base ();} template inline bool operator!= (const vector_iterator& x, const typename vector_iterator::const_iterator_type& y) {return x._base () != y;} template inline bool operator!= (const typename vector_iterator::const_iterator_type& x, const vector_iterator& y) {return x != y._base ();} // operator> // template inline bool operator> (const vector_iterator& x, const vector_iterator& y) {return x._base () > y._base ();} template inline bool operator> (const vector_iterator& x, const typename vector_iterator::const_iterator_type& y) {return x._base () > y;} template inline bool operator> (const typename vector_iterator::const_iterator_type& x, const vector_iterator& y) {return x > y._base ();} // operator>= // template inline bool operator>= (const vector_iterator& x, const vector_iterator& y) {return x._base () >= y._base ();} template inline bool operator>= (const vector_iterator& x, const typename vector_iterator::const_iterator_type& y) {return x._base () >= y;} template inline bool operator>= (const typename vector_iterator::const_iterator_type& x, const vector_iterator& y) {return x >= y._base ();} // operator<= // template inline bool operator<= (const vector_iterator& x, const vector_iterator& y) {return x._base () <= y._base ();} template inline bool operator<= (const vector_iterator& x, const typename vector_iterator::const_iterator_type& y) {return x._base () <= y;} template inline bool operator<= (const typename vector_iterator::const_iterator_type& x, const vector_iterator& y) {return x <= y._base ();} // operator- // template inline typename vector_iterator::difference_type operator-(const vector_iterator& x, const vector_iterator& y) {return x._base () - y._base ();} template inline typename vector_iterator::difference_type operator-(const vector_iterator& x, const typename vector_iterator::const_iterator_type& y) {return x._base () - y;} template inline typename vector_iterator::difference_type operator-(const typename vector_iterator::const_iterator_type& x, const vector_iterator& y) {return x - y._base ();} // operator+ // template inline vector_iterator operator+(typename vector_iterator::difference_type n, const vector_iterator& x) {return vector_iterator (x.vector (), n + x._base ());} } namespace std { template inline void swap(odb::vector& x, odb::vector& y) {x.swap (y);} } #include #include #include #endif // ODB_VECTOR_HXX