00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 #ifndef _GLIBCXX_DEBUG_DEQUE
00032 #define _GLIBCXX_DEBUG_DEQUE 1
00033
00034 #include <deque>
00035 #include <debug/safe_sequence.h>
00036 #include <debug/safe_iterator.h>
00037
00038 namespace __gnu_debug_def
00039 {
00040 template<typename _Tp, typename _Allocator = std::allocator<_Tp> >
00041 class deque
00042 : public _GLIBCXX_STD::deque<_Tp, _Allocator>,
00043 public __gnu_debug::_Safe_sequence<deque<_Tp, _Allocator> >
00044 {
00045 typedef _GLIBCXX_STD::deque<_Tp, _Allocator> _Base;
00046 typedef __gnu_debug::_Safe_sequence<deque> _Safe_base;
00047
00048 public:
00049 typedef typename _Allocator::reference reference;
00050 typedef typename _Allocator::const_reference const_reference;
00051
00052 typedef __gnu_debug::_Safe_iterator<typename _Base::iterator,deque>
00053 iterator;
00054 typedef __gnu_debug::_Safe_iterator<typename _Base::const_iterator,deque>
00055 const_iterator;
00056
00057 typedef typename _Base::size_type size_type;
00058 typedef typename _Base::difference_type difference_type;
00059
00060 typedef _Tp value_type;
00061 typedef _Allocator allocator_type;
00062 typedef typename _Allocator::pointer pointer;
00063 typedef typename _Allocator::const_pointer const_pointer;
00064 typedef std::reverse_iterator<iterator> reverse_iterator;
00065 typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
00066
00067
00068 explicit deque(const _Allocator& __a = _Allocator())
00069 : _Base(__a) { }
00070
00071 explicit deque(size_type __n, const _Tp& __value = _Tp(),
00072 const _Allocator& __a = _Allocator())
00073 : _Base(__n, __value, __a) { }
00074
00075 template<class _InputIterator>
00076 deque(_InputIterator __first, _InputIterator __last,
00077 const _Allocator& __a = _Allocator())
00078 : _Base(__gnu_debug::__check_valid_range(__first, __last), __last, __a)
00079 { }
00080
00081 deque(const deque<_Tp,_Allocator>& __x) : _Base(__x), _Safe_base() { }
00082
00083 deque(const _Base& __x) : _Base(__x), _Safe_base() { }
00084
00085 ~deque() { }
00086
00087 deque<_Tp,_Allocator>&
00088 operator=(const deque<_Tp,_Allocator>& __x)
00089 {
00090 *static_cast<_Base*>(this) = __x;
00091 this->_M_invalidate_all();
00092 return *this;
00093 }
00094
00095 template<class _InputIterator>
00096 void
00097 assign(_InputIterator __first, _InputIterator __last)
00098 {
00099 __glibcxx_check_valid_range(__first, __last);
00100 _Base::assign(__first, __last);
00101 this->_M_invalidate_all();
00102 }
00103
00104 void
00105 assign(size_type __n, const _Tp& __t)
00106 {
00107 _Base::assign(__n, __t);
00108 this->_M_invalidate_all();
00109 }
00110
00111 using _Base::get_allocator;
00112
00113
00114 iterator
00115 begin()
00116 { return iterator(_Base::begin(), this); }
00117
00118 const_iterator
00119 begin() const
00120 { return const_iterator(_Base::begin(), this); }
00121
00122 iterator
00123 end()
00124 { return iterator(_Base::end(), this); }
00125
00126 const_iterator
00127 end() const
00128 { return const_iterator(_Base::end(), this); }
00129
00130 reverse_iterator
00131 rbegin()
00132 { return reverse_iterator(end()); }
00133
00134 const_reverse_iterator
00135 rbegin() const
00136 { return const_reverse_iterator(end()); }
00137
00138 reverse_iterator
00139 rend()
00140 { return reverse_iterator(begin()); }
00141
00142 const_reverse_iterator
00143 rend() const
00144 { return const_reverse_iterator(begin()); }
00145
00146
00147 using _Base::size;
00148 using _Base::max_size;
00149
00150 void
00151 resize(size_type __sz, _Tp __c = _Tp())
00152 {
00153 typedef typename _Base::const_iterator _Base_const_iterator;
00154 typedef __gnu_debug::_After_nth_from<_Base_const_iterator> _After_nth;
00155
00156 bool __invalidate_all = __sz > this->size();
00157 if (__sz < this->size())
00158 this->_M_invalidate_if(_After_nth(__sz, _M_base().begin()));
00159
00160 _Base::resize(__sz, __c);
00161
00162 if (__invalidate_all)
00163 this->_M_invalidate_all();
00164 }
00165
00166 using _Base::empty;
00167
00168
00169 reference
00170 operator[](size_type __n)
00171 {
00172 __glibcxx_check_subscript(__n);
00173 return _M_base()[__n];
00174 }
00175
00176 const_reference
00177 operator[](size_type __n) const
00178 {
00179 __glibcxx_check_subscript(__n);
00180 return _M_base()[__n];
00181 }
00182
00183 using _Base::at;
00184
00185 reference
00186 front()
00187 {
00188 __glibcxx_check_nonempty();
00189 return _Base::front();
00190 }
00191
00192 const_reference
00193 front() const
00194 {
00195 __glibcxx_check_nonempty();
00196 return _Base::front();
00197 }
00198
00199 reference
00200 back()
00201 {
00202 __glibcxx_check_nonempty();
00203 return _Base::back();
00204 }
00205
00206 const_reference
00207 back() const
00208 {
00209 __glibcxx_check_nonempty();
00210 return _Base::back();
00211 }
00212
00213
00214 void
00215 push_front(const _Tp& __x)
00216 {
00217 _Base::push_front(__x);
00218 this->_M_invalidate_all();
00219 }
00220
00221 void
00222 push_back(const _Tp& __x)
00223 {
00224 _Base::push_back(__x);
00225 this->_M_invalidate_all();
00226 }
00227
00228 iterator
00229 insert(iterator __position, const _Tp& __x)
00230 {
00231 __glibcxx_check_insert(__position);
00232 typename _Base::iterator __res = _Base::insert(__position.base(), __x);
00233 this->_M_invalidate_all();
00234 return iterator(__res, this);
00235 }
00236
00237 void
00238 insert(iterator __position, size_type __n, const _Tp& __x)
00239 {
00240 __glibcxx_check_insert(__position);
00241 _Base::insert(__position.base(), __n, __x);
00242 this->_M_invalidate_all();
00243 }
00244
00245 template<class _InputIterator>
00246 void
00247 insert(iterator __position,
00248 _InputIterator __first, _InputIterator __last)
00249 {
00250 __glibcxx_check_insert_range(__position, __first, __last);
00251 _Base::insert(__position.base(), __first, __last);
00252 this->_M_invalidate_all();
00253 }
00254
00255 void
00256 pop_front()
00257 {
00258 __glibcxx_check_nonempty();
00259 iterator __victim = begin();
00260 __victim._M_invalidate();
00261 _Base::pop_front();
00262 }
00263
00264 void
00265 pop_back()
00266 {
00267 __glibcxx_check_nonempty();
00268 iterator __victim = end();
00269 --__victim;
00270 __victim._M_invalidate();
00271 _Base::pop_back();
00272 }
00273
00274 iterator
00275 erase(iterator __position)
00276 {
00277 __glibcxx_check_erase(__position);
00278 if (__position == begin() || __position == end()-1)
00279 {
00280 __position._M_invalidate();
00281 return iterator(_Base::erase(__position.base()), this);
00282 }
00283 else
00284 {
00285 typename _Base::iterator __res = _Base::erase(__position.base());
00286 this->_M_invalidate_all();
00287 return iterator(__res, this);
00288 }
00289 }
00290
00291 iterator
00292 erase(iterator __first, iterator __last)
00293 {
00294
00295
00296 __glibcxx_check_erase_range(__first, __last);
00297 if (__first == begin() || __last == end())
00298 {
00299 this->_M_detach_singular();
00300 for (iterator __position = __first; __position != __last; )
00301 {
00302 iterator __victim = __position++;
00303 __victim._M_invalidate();
00304 }
00305 try
00306 {
00307 return iterator(_Base::erase(__first.base(), __last.base()),
00308 this);
00309 }
00310 catch (...)
00311 {
00312 this->_M_revalidate_singular();
00313 __throw_exception_again;
00314 }
00315 }
00316 else
00317 {
00318 typename _Base::iterator __res = _Base::erase(__first.base(),
00319 __last.base());
00320 this->_M_invalidate_all();
00321 return iterator(__res, this);
00322 }
00323 }
00324
00325 void
00326 swap(deque<_Tp,_Allocator>& __x)
00327 {
00328 _Base::swap(__x);
00329 this->_M_swap(__x);
00330 }
00331
00332 void
00333 clear()
00334 {
00335 _Base::clear();
00336 this->_M_invalidate_all();
00337 }
00338
00339 _Base&
00340 _M_base() { return *this; }
00341
00342 const _Base&
00343 _M_base() const { return *this; }
00344 };
00345
00346 template<typename _Tp, typename _Alloc>
00347 inline bool
00348 operator==(const deque<_Tp, _Alloc>& __lhs,
00349 const deque<_Tp, _Alloc>& __rhs)
00350 { return __lhs._M_base() == __rhs._M_base(); }
00351
00352 template<typename _Tp, typename _Alloc>
00353 inline bool
00354 operator!=(const deque<_Tp, _Alloc>& __lhs,
00355 const deque<_Tp, _Alloc>& __rhs)
00356 { return __lhs._M_base() != __rhs._M_base(); }
00357
00358 template<typename _Tp, typename _Alloc>
00359 inline bool
00360 operator<(const deque<_Tp, _Alloc>& __lhs, const deque<_Tp, _Alloc>& __rhs)
00361 { return __lhs._M_base() < __rhs._M_base(); }
00362
00363 template<typename _Tp, typename _Alloc>
00364 inline bool
00365 operator<=(const deque<_Tp, _Alloc>& __lhs,
00366 const deque<_Tp, _Alloc>& __rhs)
00367 { return __lhs._M_base() <= __rhs._M_base(); }
00368
00369 template<typename _Tp, typename _Alloc>
00370 inline bool
00371 operator>=(const deque<_Tp, _Alloc>& __lhs,
00372 const deque<_Tp, _Alloc>& __rhs)
00373 { return __lhs._M_base() >= __rhs._M_base(); }
00374
00375 template<typename _Tp, typename _Alloc>
00376 inline bool
00377 operator>(const deque<_Tp, _Alloc>& __lhs, const deque<_Tp, _Alloc>& __rhs)
00378 { return __lhs._M_base() > __rhs._M_base(); }
00379
00380 template<typename _Tp, typename _Alloc>
00381 inline void
00382 swap(deque<_Tp, _Alloc>& __lhs, deque<_Tp, _Alloc>& __rhs)
00383 { __lhs.swap(__rhs); }
00384 }
00385
00386 #endif