stl_iterator.h

Go to the documentation of this file.
00001 // Iterators -*- C++ -*-
00002 
00003 // Copyright (C) 2001, 2002 Free Software Foundation, Inc.
00004 //
00005 // This file is part of the GNU ISO C++ Library.  This library is free
00006 // software; you can redistribute it and/or modify it under the
00007 // terms of the GNU General Public License as published by the
00008 // Free Software Foundation; either version 2, or (at your option)
00009 // any later version.
00010 
00011 // This library is distributed in the hope that it will be useful,
00012 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00013 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00014 // GNU General Public License for more details.
00015 
00016 // You should have received a copy of the GNU General Public License along
00017 // with this library; see the file COPYING.  If not, write to the Free
00018 // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
00019 // USA.
00020 
00021 // As a special exception, you may use this file as part of a free software
00022 // library without restriction.  Specifically, if other files instantiate
00023 // templates or use macros or inline functions from this file, or you compile
00024 // this file and link it with other files to produce an executable, this
00025 // file does not by itself cause the resulting executable to be covered by
00026 // the GNU General Public License.  This exception does not however
00027 // invalidate any other reasons why the executable file might be covered by
00028 // the GNU General Public License.
00029 
00030 /*
00031  *
00032  * Copyright (c) 1994
00033  * Hewlett-Packard Company
00034  *
00035  * Permission to use, copy, modify, distribute and sell this software
00036  * and its documentation for any purpose is hereby granted without fee,
00037  * provided that the above copyright notice appear in all copies and
00038  * that both that copyright notice and this permission notice appear
00039  * in supporting documentation.  Hewlett-Packard Company makes no
00040  * representations about the suitability of this software for any
00041  * purpose.  It is provided "as is" without express or implied warranty.
00042  *
00043  *
00044  * Copyright (c) 1996-1998
00045  * Silicon Graphics Computer Systems, Inc.
00046  *
00047  * Permission to use, copy, modify, distribute and sell this software
00048  * and its documentation for any purpose is hereby granted without fee,
00049  * provided that the above copyright notice appear in all copies and
00050  * that both that copyright notice and this permission notice appear
00051  * in supporting documentation.  Silicon Graphics makes no
00052  * representations about the suitability of this software for any
00053  * purpose.  It is provided "as is" without express or implied warranty.
00054  */
00055 
00065 #ifndef __GLIBCPP_INTERNAL_ITERATOR_H
00066 #define __GLIBCPP_INTERNAL_ITERATOR_H
00067 
00068 namespace std
00069 {
00070   // 24.4.1 Reverse iterators
00089   template<typename _Iterator>
00090     class reverse_iterator 
00091     : public iterator<typename iterator_traits<_Iterator>::iterator_category,
00092               typename iterator_traits<_Iterator>::value_type,
00093               typename iterator_traits<_Iterator>::difference_type,
00094               typename iterator_traits<_Iterator>::pointer,
00095                       typename iterator_traits<_Iterator>::reference>
00096     {
00097     protected:
00098       _Iterator current;
00099 
00100     public:
00101       typedef _Iterator                        iterator_type;
00102       typedef typename iterator_traits<_Iterator>::difference_type  
00103                                        difference_type;
00104       typedef typename iterator_traits<_Iterator>::reference   reference;
00105       typedef typename iterator_traits<_Iterator>::pointer     pointer;
00106 
00107     public:
00111       reverse_iterator() { }
00112 
00116       explicit 
00117       reverse_iterator(iterator_type __x) : current(__x) { }
00118 
00122       reverse_iterator(const reverse_iterator& __x) 
00123       : current(__x.current) { }
00124 
00129       template<typename _Iter>
00130         reverse_iterator(const reverse_iterator<_Iter>& __x)
00131     : current(__x.base()) { }
00132     
00136       iterator_type 
00137       base() const { return current; }
00138 
00144       reference 
00145       operator*() const 
00146       {
00147     _Iterator __tmp = current;
00148     return *--__tmp;
00149       }
00150 
00156       pointer 
00157       operator->() const { return &(operator*()); }
00158 
00164       reverse_iterator& 
00165       operator++() 
00166       {
00167     --current;
00168     return *this;
00169       }
00170 
00176       reverse_iterator 
00177       operator++(int) 
00178       {
00179     reverse_iterator __tmp = *this;
00180     --current;
00181     return __tmp;
00182       }
00183 
00189       reverse_iterator& 
00190       operator--() 
00191       {
00192     ++current;
00193     return *this;
00194       }
00195 
00201       reverse_iterator operator--(int) 
00202       {
00203     reverse_iterator __tmp = *this;
00204     ++current;
00205     return __tmp;
00206       }
00207       
00213       reverse_iterator 
00214       operator+(difference_type __n) const 
00215       { return reverse_iterator(current - __n); }
00216 
00222       reverse_iterator& 
00223       operator+=(difference_type __n) 
00224       {
00225     current -= __n;
00226     return *this;
00227       }
00228 
00234       reverse_iterator 
00235       operator-(difference_type __n) const 
00236       { return reverse_iterator(current + __n); }
00237 
00243       reverse_iterator& 
00244       operator-=(difference_type __n) 
00245       {
00246     current += __n;
00247     return *this;
00248       }
00249 
00255       reference 
00256       operator[](difference_type __n) const { return *(*this + __n); }  
00257     }; 
00258  
00260 
00269   template<typename _Iterator>
00270     inline bool 
00271     operator==(const reverse_iterator<_Iterator>& __x, 
00272            const reverse_iterator<_Iterator>& __y) 
00273     { return __x.base() == __y.base(); }
00274 
00275   template<typename _Iterator>
00276     inline bool 
00277     operator<(const reverse_iterator<_Iterator>& __x, 
00278           const reverse_iterator<_Iterator>& __y) 
00279     { return __y.base() < __x.base(); }
00280 
00281   template<typename _Iterator>
00282     inline bool 
00283     operator!=(const reverse_iterator<_Iterator>& __x, 
00284            const reverse_iterator<_Iterator>& __y) 
00285     { return !(__x == __y); }
00286 
00287   template<typename _Iterator>
00288     inline bool 
00289     operator>(const reverse_iterator<_Iterator>& __x, 
00290           const reverse_iterator<_Iterator>& __y) 
00291     { return __y < __x; }
00292 
00293   template<typename _Iterator>
00294     inline bool 
00295     operator<=(const reverse_iterator<_Iterator>& __x, 
00296         const reverse_iterator<_Iterator>& __y) 
00297     { return !(__y < __x); }
00298 
00299   template<typename _Iterator>
00300     inline bool 
00301     operator>=(const reverse_iterator<_Iterator>& __x, 
00302            const reverse_iterator<_Iterator>& __y) 
00303     { return !(__x < __y); }
00304 
00305   template<typename _Iterator>
00306     inline typename reverse_iterator<_Iterator>::difference_type
00307     operator-(const reverse_iterator<_Iterator>& __x, 
00308           const reverse_iterator<_Iterator>& __y) 
00309     { return __y.base() - __x.base(); }
00310 
00311   template<typename _Iterator>
00312     inline reverse_iterator<_Iterator> 
00313     operator+(typename reverse_iterator<_Iterator>::difference_type __n,
00314           const reverse_iterator<_Iterator>& __x) 
00315     { return reverse_iterator<_Iterator>(__x.base() - __n); }
00317 
00318   // 24.4.2.2.1 back_insert_iterator
00329   template<typename _Container>
00330     class back_insert_iterator 
00331     : public iterator<output_iterator_tag, void, void, void, void>
00332     {
00333     protected:
00334       _Container* container;
00335 
00336     public:
00338       typedef _Container          container_type;
00339       
00341       explicit 
00342       back_insert_iterator(_Container& __x) : container(&__x) { }
00343 
00355       back_insert_iterator&
00356       operator=(typename _Container::const_reference __value) 
00357       { 
00358     container->push_back(__value);
00359     return *this;
00360       }
00361 
00363       back_insert_iterator& 
00364       operator*() { return *this; }
00365 
00367       back_insert_iterator& 
00368       operator++() { return *this; }
00369 
00371       back_insert_iterator
00372       operator++(int) { return *this; }
00373     };
00374 
00386   template<typename _Container>
00387     inline back_insert_iterator<_Container> 
00388     back_inserter(_Container& __x) 
00389     { return back_insert_iterator<_Container>(__x); }
00390 
00401   template<typename _Container>
00402     class front_insert_iterator 
00403     : public iterator<output_iterator_tag, void, void, void, void>
00404     {
00405     protected:
00406       _Container* container;
00407 
00408     public:
00410       typedef _Container          container_type;
00411 
00413       explicit front_insert_iterator(_Container& __x) : container(&__x) { }
00414 
00426       front_insert_iterator&
00427       operator=(typename _Container::const_reference __value) 
00428       { 
00429     container->push_front(__value);
00430     return *this;
00431       }
00432 
00434       front_insert_iterator& 
00435       operator*() { return *this; }
00436 
00438       front_insert_iterator& 
00439       operator++() { return *this; }
00440 
00442       front_insert_iterator 
00443       operator++(int) { return *this; }
00444     };
00445 
00457   template<typename _Container>
00458     inline front_insert_iterator<_Container> 
00459     front_inserter(_Container& __x) 
00460     { return front_insert_iterator<_Container>(__x); }
00461 
00476   template<typename _Container>
00477     class insert_iterator 
00478     : public iterator<output_iterator_tag, void, void, void, void>
00479     {
00480     protected:
00481       _Container* container;
00482       typename _Container::iterator iter;
00483 
00484     public:
00486       typedef _Container          container_type;
00487       
00492       insert_iterator(_Container& __x, typename _Container::iterator __i) 
00493       : container(&__x), iter(__i) {}
00494    
00518       insert_iterator&
00519       operator=(const typename _Container::const_reference __value) 
00520       { 
00521     iter = container->insert(iter, __value);
00522     ++iter;
00523     return *this;
00524       }
00525 
00527       insert_iterator& 
00528       operator*() { return *this; }
00529 
00531       insert_iterator& 
00532       operator++() { return *this; }
00533 
00535       insert_iterator& 
00536       operator++(int) { return *this; }
00537     };
00538   
00550   template<typename _Container, typename _Iterator>
00551     inline insert_iterator<_Container> 
00552     inserter(_Container& __x, _Iterator __i)
00553     {
00554       return insert_iterator<_Container>(__x, 
00555                      typename _Container::iterator(__i));
00556     }
00557 } // namespace std
00558 
00559 namespace __gnu_cxx
00560 {  
00561   // This iterator adapter is 'normal' in the sense that it does not
00562   // change the semantics of any of the operators of its iterator
00563   // parameter.  Its primary purpose is to convert an iterator that is
00564   // not a class, e.g. a pointer, into an iterator that is a class.
00565   // The _Container parameter exists solely so that different containers
00566   // using this template can instantiate different types, even if the
00567   // _Iterator parameter is the same.
00568   using std::iterator_traits;
00569   using std::iterator;
00570   template<typename _Iterator, typename _Container>
00571     class __normal_iterator
00572       : public iterator<typename iterator_traits<_Iterator>::iterator_category,
00573                         typename iterator_traits<_Iterator>::value_type,
00574                         typename iterator_traits<_Iterator>::difference_type,
00575                         typename iterator_traits<_Iterator>::pointer,
00576                         typename iterator_traits<_Iterator>::reference>
00577     {
00578     protected:
00579       _Iterator _M_current;
00580       
00581     public:
00582       typedef typename iterator_traits<_Iterator>::difference_type  
00583                                        difference_type;
00584       typedef typename iterator_traits<_Iterator>::reference   reference;
00585       typedef typename iterator_traits<_Iterator>::pointer     pointer;
00586 
00587       __normal_iterator() : _M_current(_Iterator()) { }
00588 
00589       explicit 
00590       __normal_iterator(const _Iterator& __i) : _M_current(__i) { }
00591 
00592       // Allow iterator to const_iterator conversion
00593       template<typename _Iter>
00594       inline __normal_iterator(const __normal_iterator<_Iter, _Container>& __i)
00595     : _M_current(__i.base()) { }
00596 
00597       // Forward iterator requirements
00598       reference
00599       operator*() const { return *_M_current; }
00600       
00601       pointer
00602       operator->() const { return _M_current; }
00603       
00604       __normal_iterator&
00605       operator++() { ++_M_current; return *this; }
00606       
00607       __normal_iterator
00608       operator++(int) { return __normal_iterator(_M_current++); }
00609       
00610       // Bidirectional iterator requirements
00611       __normal_iterator&
00612       operator--() { --_M_current; return *this; }
00613       
00614       __normal_iterator
00615       operator--(int) { return __normal_iterator(_M_current--); }
00616       
00617       // Random access iterator requirements
00618       reference
00619       operator[](const difference_type& __n) const
00620       { return _M_current[__n]; }
00621       
00622       __normal_iterator&
00623       operator+=(const difference_type& __n)
00624       { _M_current += __n; return *this; }
00625 
00626       __normal_iterator
00627       operator+(const difference_type& __n) const
00628       { return __normal_iterator(_M_current + __n); }
00629       
00630       __normal_iterator&
00631       operator-=(const difference_type& __n)
00632       { _M_current -= __n; return *this; }
00633       
00634       __normal_iterator
00635       operator-(const difference_type& __n) const
00636       { return __normal_iterator(_M_current - __n); }
00637       
00638       const _Iterator& 
00639       base() const { return _M_current; }
00640     };
00641 
00642   // Note: In what follows, the left- and right-hand-side iterators are
00643   // allowed to vary in types (conceptually in cv-qualification) so that
00644   // comparaison between cv-qualified and non-cv-qualified iterators be
00645   // valid.  However, the greedy and unfriendly operators in std::rel_ops
00646   // will make overload resolution ambiguous (when in scope) if we don't
00647   // provide overloads whose operands are of the same type.  Can someone
00648   // remind me what generic programming is about? -- Gaby
00649   
00650   // Forward iterator requirements
00651   template<typename _IteratorL, typename _IteratorR, typename _Container>
00652   inline bool
00653   operator==(const __normal_iterator<_IteratorL, _Container>& __lhs,
00654          const __normal_iterator<_IteratorR, _Container>& __rhs)
00655   { return __lhs.base() == __rhs.base(); }
00656 
00657   template<typename _Iterator, typename _Container>
00658   inline bool
00659   operator==(const __normal_iterator<_Iterator, _Container>& __lhs,
00660              const __normal_iterator<_Iterator, _Container>& __rhs)
00661   { return __lhs.base() == __rhs.base(); }
00662 
00663   template<typename _IteratorL, typename _IteratorR, typename _Container>
00664   inline bool
00665   operator!=(const __normal_iterator<_IteratorL, _Container>& __lhs,
00666          const __normal_iterator<_IteratorR, _Container>& __rhs)
00667   { return __lhs.base() != __rhs.base(); }
00668 
00669   template<typename _Iterator, typename _Container>
00670   inline bool
00671   operator!=(const __normal_iterator<_Iterator, _Container>& __lhs,
00672              const __normal_iterator<_Iterator, _Container>& __rhs)
00673   { return __lhs.base() != __rhs.base(); }
00674 
00675   // Random access iterator requirements
00676   template<typename _IteratorL, typename _IteratorR, typename _Container>
00677   inline bool 
00678   operator<(const __normal_iterator<_IteratorL, _Container>& __lhs,
00679         const __normal_iterator<_IteratorR, _Container>& __rhs)
00680   { return __lhs.base() < __rhs.base(); }
00681 
00682   template<typename _Iterator, typename _Container>
00683   inline bool
00684   operator<(const __normal_iterator<_Iterator, _Container>& __lhs,
00685              const __normal_iterator<_Iterator, _Container>& __rhs)
00686   { return __lhs.base() < __rhs.base(); }
00687 
00688   template<typename _IteratorL, typename _IteratorR, typename _Container>
00689   inline bool
00690   operator>(const __normal_iterator<_IteratorL, _Container>& __lhs,
00691         const __normal_iterator<_IteratorR, _Container>& __rhs)
00692   { return __lhs.base() > __rhs.base(); }
00693 
00694   template<typename _Iterator, typename _Container>
00695   inline bool
00696   operator>(const __normal_iterator<_Iterator, _Container>& __lhs,
00697         const __normal_iterator<_Iterator, _Container>& __rhs)
00698   { return __lhs.base() > __rhs.base(); }
00699 
00700   template<typename _IteratorL, typename _IteratorR, typename _Container>
00701   inline bool
00702   operator<=(const __normal_iterator<_IteratorL, _Container>& __lhs,
00703          const __normal_iterator<_IteratorR, _Container>& __rhs)
00704   { return __lhs.base() <= __rhs.base(); }
00705 
00706   template<typename _Iterator, typename _Container>
00707   inline bool
00708   operator<=(const __normal_iterator<_Iterator, _Container>& __lhs,
00709          const __normal_iterator<_Iterator, _Container>& __rhs)
00710   { return __lhs.base() <= __rhs.base(); }
00711 
00712   template<typename _IteratorL, typename _IteratorR, typename _Container>
00713   inline bool
00714   operator>=(const __normal_iterator<_IteratorL, _Container>& __lhs,
00715          const __normal_iterator<_IteratorR, _Container>& __rhs)
00716   { return __lhs.base() >= __rhs.base(); }
00717 
00718   template<typename _Iterator, typename _Container>
00719   inline bool
00720   operator>=(const __normal_iterator<_Iterator, _Container>& __lhs,
00721          const __normal_iterator<_Iterator, _Container>& __rhs)
00722   { return __lhs.base() >= __rhs.base(); }
00723 
00724   // _GLIBCPP_RESOLVE_LIB_DEFECTS
00725   // According to the resolution of DR179 not only the various comparison
00726   // operators but also operator- must accept mixed iterator/const_iterator
00727   // parameters.
00728   template<typename _IteratorL, typename _IteratorR, typename _Container>
00729   inline typename __normal_iterator<_IteratorL, _Container>::difference_type
00730   operator-(const __normal_iterator<_IteratorL, _Container>& __lhs,
00731          const __normal_iterator<_IteratorR, _Container>& __rhs)
00732   { return __lhs.base() - __rhs.base(); }
00733 
00734   template<typename _Iterator, typename _Container>
00735   inline __normal_iterator<_Iterator, _Container>
00736   operator+(typename __normal_iterator<_Iterator, _Container>::difference_type __n,
00737         const __normal_iterator<_Iterator, _Container>& __i)
00738   { return __normal_iterator<_Iterator, _Container>(__i.base() + __n); }
00739 } // namespace __gnu_cxx
00740 
00741 #endif 
00742 
00743 // Local Variables:
00744 // mode:C++
00745 // End:

Generated on Tue Apr 29 20:16:23 2003 for libstdc++-v3 Source by doxygen1.3