# set.h

Go to the documentation of this file.

    00001 // Debugging set implementation -*- C++ -*-
    00002
    00003 // Copyright (C) 2003, 2004, 2005, 2006, 2007, 2009
    00004 // Free Software Foundation, Inc.
    00005 //
    00006 // This file is part of the GNU ISO C++ Library.  This library is free
    00007 // software; you can redistribute it and/or modify it under the
    00008 // terms of the GNU General Public License as published by the
    00009 // Free Software Foundation; either version 3, or (at your option)
    00010 // any later version.
    00011
    00012 // This library is distributed in the hope that it will be useful,
    00013 // but WITHOUT ANY WARRANTY; without even the implied warranty of
    00014 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    00015 // GNU General Public License for more details.
    00016
    00017 // Under Section 7 of GPL version 3, you are granted additional
    00018 // permissions described in the GCC Runtime Library Exception, version
    00019 // 3.1, as published by the Free Software Foundation.
    00020
    00021 // You should have received a copy of the GNU General Public License and
    00022 // a copy of the GCC Runtime Library Exception along with this program;
    00023 // see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
    00024 // <http://www.gnu.org/licenses/>.
    00025
    00026 /** @file debug/set.h
    00027  *  This file is a GNU debug extension to the Standard C++ Library.
    00028  */
    00029
    00030 #ifndef _GLIBCXX_DEBUG_SET_H
    00031 #define _GLIBCXX_DEBUG_SET_H 1
    00032
    00033 #include <debug/safe_sequence.h>
    00034 #include <debug/safe_iterator.h>
    00035 #include <utility>
    00036
    00037 namespace std
    00038 {
    00039 namespace __debug
    00040 {
    00041   template<typename _Key, typename _Compare = std::less<_Key>,
    00042        typename _Allocator = std::allocator<_Key> >
    00043     class set
    00044     : public _GLIBCXX_STD_D::set<_Key,_Compare,_Allocator>,
    00045       public __gnu_debug::_Safe_sequence<set<_Key, _Compare, _Allocator> >
    00046     {
    00047       typedef _GLIBCXX_STD_D::set<_Key, _Compare, _Allocator> _Base;
    00048       typedef __gnu_debug::_Safe_sequence<set> _Safe_base;
    00049
    00050     public:
    00051       // types:
    00052       typedef _Key                  key_type;
    00053       typedef _Key                  value_type;
    00054       typedef _Compare                  key_compare;
    00055       typedef _Compare                  value_compare;
    00056       typedef _Allocator                allocator_type;
    00057       typedef typename _Base::reference             reference;
    00058       typedef typename _Base::const_reference       const_reference;
    00059
    00060       typedef __gnu_debug::_Safe_iterator<typename _Base::iterator, set>
    00061                                                     iterator;
    00062       typedef __gnu_debug::_Safe_iterator<typename _Base::const_iterator, set>
    00063                                                     const_iterator;
    00064
    00065       typedef typename _Base::size_type             size_type;
    00066       typedef typename _Base::difference_type       difference_type;
    00067       typedef typename _Base::pointer               pointer;
    00068       typedef typename _Base::const_pointer         const_pointer;
    00069       typedef std::reverse_iterator<iterator>       reverse_iterator;
    00070       typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
    00071
    00072       // 23.3.3.1 construct/copy/destroy:
    00073       explicit set(const _Compare& __comp = _Compare(),
    00074            const _Allocator& __a = _Allocator())
    00075       : _Base(__comp, __a) { }
    00076
    00077       template<typename _InputIterator>
    00078         set(_InputIterator __first, _InputIterator __last,
    00079         const _Compare& __comp = _Compare(),
    00080         const _Allocator& __a = _Allocator())
    00081     : _Base(__gnu_debug::__check_valid_range(__first, __last), __last,
    00082         __comp, __a) { }
    00083
    00084       set(const set& __x)
    00085       : _Base(__x), _Safe_base() { }
    00086
    00087       set(const _Base& __x)
    00088       : _Base(__x), _Safe_base() { }
    00089
    00090 #ifdef __GXX_EXPERIMENTAL_CXX0X__
    00091       set(set&& __x)
    00092       : _Base(std::forward<set>(__x)), _Safe_base()
    00093       { this->_M_swap(__x); }
    00094
    00095       set(initializer_list<value_type> __l,
    00096       const _Compare& __comp = _Compare(),
    00097       const allocator_type& __a = allocator_type())
    00098       : _Base(__l, __comp, __a), _Safe_base() { }
    00099 #endif
    00100
    00101       ~set() { }
    00102
    00103       set&
    00104       operator=(const set& __x)
    00105       {
    00106     *static_cast<_Base*>(this) = __x;
    00107     this->_M_invalidate_all();
    00108     return *this;
    00109       }
    00110
    00111 #ifdef __GXX_EXPERIMENTAL_CXX0X__
    00112       set&
    00113       operator=(set&& __x)
    00114       {
    00115         // NB: DR 675.
    00116     clear();
    00117     swap(__x);
    00118     return *this;
    00119       }
    00120
    00121       set&
    00122       operator=(initializer_list<value_type> __l)
    00123       {
    00124     this->clear();
    00125     this->insert(__l);
    00126     return *this;
    00127       }
    00128 #endif
    00129
    00130       using _Base::get_allocator;
    00131
    00132       // iterators:
    00133       iterator
    00134       begin()
    00135       { return iterator(_Base::begin(), this); }
    00136
    00137       const_iterator
    00138       begin() const
    00139       { return const_iterator(_Base::begin(), this); }
    00140
    00141       iterator
    00142       end()
    00143       { return iterator(_Base::end(), this); }
    00144
    00145       const_iterator
    00146       end() const
    00147       { return const_iterator(_Base::end(), this); }
    00148
    00149       reverse_iterator
    00150       rbegin()
    00151       { return reverse_iterator(end()); }
    00152
    00153       const_reverse_iterator
    00154       rbegin() const
    00155       { return const_reverse_iterator(end()); }
    00156
    00157       reverse_iterator
    00158       rend()
    00159       { return reverse_iterator(begin()); }
    00160
    00161       const_reverse_iterator
    00162       rend() const
    00163       { return const_reverse_iterator(begin()); }
    00164
    00165 #ifdef __GXX_EXPERIMENTAL_CXX0X__
    00166       const_iterator
    00167       cbegin() const
    00168       { return const_iterator(_Base::begin(), this); }
    00169
    00170       const_iterator
    00171       cend() const
    00172       { return const_iterator(_Base::end(), this); }
    00173
    00174       const_reverse_iterator
    00175       crbegin() const
    00176       { return const_reverse_iterator(end()); }
    00177
    00178       const_reverse_iterator
    00179       crend() const
    00180       { return const_reverse_iterator(begin()); }
    00181 #endif
    00182
    00183       // capacity:
    00184       using _Base::empty;
    00185       using _Base::size;
    00186       using _Base::max_size;
    00187
    00188       // modifiers:
    00189       std::pair<iterator, bool>
    00190       insert(const value_type& __x)
    00191       {
    00192     typedef typename _Base::iterator _Base_iterator;
    00193     std::pair<_Base_iterator, bool> __res = _Base::insert(__x);
    00194     return std::pair<iterator, bool>(iterator(__res.first, this),
    00195                      __res.second);
    00196       }
    00197
    00198       iterator
    00199       insert(iterator __position, const value_type& __x)
    00200       {
    00201     __glibcxx_check_insert(__position);
    00202     return iterator(_Base::insert(__position.base(), __x), this);
    00203       }
    00204
    00205       template <typename _InputIterator>
    00206         void
    00207         insert(_InputIterator __first, _InputIterator __last)
    00208         {
    00209       __glibcxx_check_valid_range(__first, __last);
    00210       _Base::insert(__first, __last);
    00211     }
    00212
    00213 #ifdef __GXX_EXPERIMENTAL_CXX0X__
    00214       void
    00215       insert(initializer_list<value_type> __l)
    00216       { _Base::insert(__l); }
    00217 #endif
    00218
    00219       void
    00220       erase(iterator __position)
    00221       {
    00222     __glibcxx_check_erase(__position);
    00223     __position._M_invalidate();
    00224     _Base::erase(__position.base());
    00225       }
    00226
    00227       size_type
    00228       erase(const key_type& __x)
    00229       {
    00230     iterator __victim = find(__x);
    00231     if (__victim == end())
    00232           return 0;
    00233     else
    00234         {
    00235       __victim._M_invalidate();
    00236       _Base::erase(__victim.base());
    00237       return 1;
    00238         }
    00239       }
    00240
    00241       void
    00242       erase(iterator __first, iterator __last)
    00243       {
    00244     // _GLIBCXX_RESOLVE_LIB_DEFECTS
    00245     // 151. can't currently clear() empty container
    00246     __glibcxx_check_erase_range(__first, __last);
    00247
    00248     while (__first != __last)
    00249         this->erase(__first++);
    00250       }
    00251
    00252       void
    00253 #ifdef __GXX_EXPERIMENTAL_CXX0X__
    00254       swap(set&& __x)
    00255 #else
    00256       swap(set& __x)
    00257 #endif
    00258       {
    00259     _Base::swap(__x);
    00260     this->_M_swap(__x);
    00261       }
    00262
    00263       void
    00264       clear()
    00265       { this->erase(begin(), end()); }
    00266
    00267       // observers:
    00268       using _Base::key_comp;
    00269       using _Base::value_comp;
    00270
    00271       // set operations:
    00272       iterator
    00273       find(const key_type& __x)
    00274       { return iterator(_Base::find(__x), this); }
    00275
    00276       // _GLIBCXX_RESOLVE_LIB_DEFECTS
    00277       // 214. set::find() missing const overload
    00278       const_iterator
    00279       find(const key_type& __x) const
    00280       { return const_iterator(_Base::find(__x), this); }
    00281
    00282       using _Base::count;
    00283
    00284       iterator
    00285       lower_bound(const key_type& __x)
    00286       { return iterator(_Base::lower_bound(__x), this); }
    00287
    00288       // _GLIBCXX_RESOLVE_LIB_DEFECTS
    00289       // 214. set::find() missing const overload
    00290       const_iterator
    00291       lower_bound(const key_type& __x) const
    00292       { return const_iterator(_Base::lower_bound(__x), this); }
    00293
    00294       iterator
    00295       upper_bound(const key_type& __x)
    00296       { return iterator(_Base::upper_bound(__x), this); }
    00297
    00298       // _GLIBCXX_RESOLVE_LIB_DEFECTS
    00299       // 214. set::find() missing const overload
    00300       const_iterator
    00301       upper_bound(const key_type& __x) const
    00302       { return const_iterator(_Base::upper_bound(__x), this); }
    00303
    00304       std::pair<iterator,iterator>
    00305       equal_range(const key_type& __x)
    00306       {
    00307     typedef typename _Base::iterator _Base_iterator;
    00308     std::pair<_Base_iterator, _Base_iterator> __res =
    00309         _Base::equal_range(__x);
    00310     return std::make_pair(iterator(__res.first, this),
    00311                   iterator(__res.second, this));
    00312       }
    00313
    00314       // _GLIBCXX_RESOLVE_LIB_DEFECTS
    00315       // 214. set::find() missing const overload
    00316       std::pair<const_iterator,const_iterator>
    00317       equal_range(const key_type& __x) const
    00318       {
    00319     typedef typename _Base::const_iterator _Base_iterator;
    00320     std::pair<_Base_iterator, _Base_iterator> __res =
    00321         _Base::equal_range(__x);
    00322     return std::make_pair(const_iterator(__res.first, this),
    00323                   const_iterator(__res.second, this));
    00324       }
    00325
    00326       _Base&
    00327       _M_base() { return *this; }
    00328
    00329       const _Base&
    00330       _M_base() const { return *this; }
    00331
    00332     private:
    00333       void
    00334       _M_invalidate_all()
    00335       {
    00336     typedef typename _Base::const_iterator _Base_const_iterator;
    00337     typedef __gnu_debug::_Not_equal_to<_Base_const_iterator> _Not_equal;
    00338     this->_M_invalidate_if(_Not_equal(_M_base().end()));
    00339       }
    00340     };
    00341
    00342   template<typename _Key, typename _Compare, typename _Allocator>
    00343     inline bool
    00344     operator==(const set<_Key, _Compare, _Allocator>& __lhs,
    00345            const set<_Key, _Compare, _Allocator>& __rhs)
    00346     { return __lhs._M_base() == __rhs._M_base(); }
    00347
    00348   template<typename _Key, typename _Compare, typename _Allocator>
    00349     inline bool
    00350     operator!=(const set<_Key, _Compare, _Allocator>& __lhs,
    00351            const set<_Key, _Compare, _Allocator>& __rhs)
    00352     { return __lhs._M_base() != __rhs._M_base(); }
    00353
    00354   template<typename _Key, typename _Compare, typename _Allocator>
    00355     inline bool
    00356     operator<(const set<_Key, _Compare, _Allocator>& __lhs,
    00357           const set<_Key, _Compare, _Allocator>& __rhs)
    00358     { return __lhs._M_base() < __rhs._M_base(); }
    00359
    00360   template<typename _Key, typename _Compare, typename _Allocator>
    00361     inline bool
    00362     operator<=(const set<_Key, _Compare, _Allocator>& __lhs,
    00363            const set<_Key, _Compare, _Allocator>& __rhs)
    00364     { return __lhs._M_base() <= __rhs._M_base(); }
    00365
    00366   template<typename _Key, typename _Compare, typename _Allocator>
    00367     inline bool
    00368     operator>=(const set<_Key, _Compare, _Allocator>& __lhs,
    00369            const set<_Key, _Compare, _Allocator>& __rhs)
    00370     { return __lhs._M_base() >= __rhs._M_base(); }
    00371
    00372   template<typename _Key, typename _Compare, typename _Allocator>
    00373     inline bool
    00374     operator>(const set<_Key, _Compare, _Allocator>& __lhs,
    00375           const set<_Key, _Compare, _Allocator>& __rhs)
    00376     { return __lhs._M_base() > __rhs._M_base(); }
    00377
    00378   template<typename _Key, typename _Compare, typename _Allocator>
    00379     void
    00380     swap(set<_Key, _Compare, _Allocator>& __x,
    00381      set<_Key, _Compare, _Allocator>& __y)
    00382     { return __x.swap(__y); }
    00383
    00384 #ifdef __GXX_EXPERIMENTAL_CXX0X__
    00385   template<typename _Key, typename _Compare, typename _Allocator>
    00386     void
    00387     swap(set<_Key, _Compare, _Allocator>&& __x,
    00388      set<_Key, _Compare, _Allocator>& __y)
    00389     { return __x.swap(__y); }
    00390
    00391   template<typename _Key, typename _Compare, typename _Allocator>
    00392     void
    00393     swap(set<_Key, _Compare, _Allocator>& __x,
    00394      set<_Key, _Compare, _Allocator>&& __y)
    00395     { return __x.swap(__y); }
    00396 #endif
    00397
    00398 } // namespace __debug
    00399 } // namespace std
    00400
    00401 #endif