stl_iter.h
上传用户:nizebo
上传日期:2022-05-14
资源大小:882k
文件大小:29k
源码类别:

STL

开发平台:

Visual C++

  1. /*
  2.  *
  3.  * Copyright (c) 1994
  4.  * Hewlett-Packard Company
  5.  *
  6.  * Permission to use, copy, modify, distribute and sell this software
  7.  * and its documentation for any purpose is hereby granted without fee,
  8.  * provided that the above copyright notice appear in all copies and
  9.  * that both that copyright notice and this permission notice appear
  10.  * in supporting documentation.  Hewlett-Packard Company makes no
  11.  * representations about the suitability of this software for any
  12.  * purpose.  It is provided "as is" without express or implied warranty.
  13.  *
  14.  *
  15.  * Copyright (c) 1996-1998
  16.  * Silicon Graphics Computer Systems, Inc.
  17.  *
  18.  * Permission to use, copy, modify, distribute and sell this software
  19.  * and its documentation for any purpose is hereby granted without fee,
  20.  * provided that the above copyright notice appear in all copies and
  21.  * that both that copyright notice and this permission notice appear
  22.  * in supporting documentation.  Silicon Graphics makes no
  23.  * representations about the suitability of this software for any
  24.  * purpose.  It is provided "as is" without express or implied warranty.
  25.  */
  26. /* NOTE: This is an internal header file, included by other STL headers.
  27.  *   You should not attempt to use it directly.
  28.  */
  29. #ifndef __SGI_STL_INTERNAL_ITERATOR_H
  30. #define __SGI_STL_INTERNAL_ITERATOR_H
  31. __STL_BEGIN_NAMESPACE
  32. template <class _Container>
  33. class back_insert_iterator {
  34. protected:
  35.   _Container* container;
  36. public:
  37.   typedef _Container          container_type;
  38.   typedef output_iterator_tag iterator_category;
  39.   typedef void                value_type;
  40.   typedef void                difference_type;
  41.   typedef void                pointer;
  42.   typedef void                reference;
  43.   explicit back_insert_iterator(_Container& __x) : container(&__x) {}
  44.   back_insert_iterator<_Container>&
  45.   operator=(const typename _Container::value_type& __value) { 
  46.     container->push_back(__value);
  47.     return *this;
  48.   }
  49.   back_insert_iterator<_Container>& operator*() { return *this; }
  50.   back_insert_iterator<_Container>& operator++() { return *this; }
  51.   back_insert_iterator<_Container>& operator++(int) { return *this; }
  52. };
  53. #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
  54. template <class _Container>
  55. inline output_iterator_tag
  56. iterator_category(const back_insert_iterator<_Container>&)
  57. {
  58.   return output_iterator_tag();
  59. }
  60. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  61. template <class _Container>
  62. inline back_insert_iterator<_Container> back_inserter(_Container& __x) {
  63.   return back_insert_iterator<_Container>(__x);
  64. }
  65. template <class _Container>
  66. class front_insert_iterator {
  67. protected:
  68.   _Container* container;
  69. public:
  70.   typedef _Container          container_type;
  71.   typedef output_iterator_tag iterator_category;
  72.   typedef void                value_type;
  73.   typedef void                difference_type;
  74.   typedef void                pointer;
  75.   typedef void                reference;
  76.   explicit front_insert_iterator(_Container& __x) : container(&__x) {}
  77.   front_insert_iterator<_Container>&
  78.   operator=(const typename _Container::value_type& __value) { 
  79.     container->push_front(__value);
  80.     return *this;
  81.   }
  82.   front_insert_iterator<_Container>& operator*() { return *this; }
  83.   front_insert_iterator<_Container>& operator++() { return *this; }
  84.   front_insert_iterator<_Container>& operator++(int) { return *this; }
  85. };
  86. #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
  87. template <class _Container>
  88. inline output_iterator_tag
  89. iterator_category(const front_insert_iterator<_Container>&)
  90. {
  91.   return output_iterator_tag();
  92. }
  93. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  94. template <class _Container>
  95. inline front_insert_iterator<_Container> front_inserter(_Container& __x) {
  96.   return front_insert_iterator<_Container>(__x);
  97. }
  98. template <class _Container>
  99. class insert_iterator {
  100. protected:
  101.   _Container* container;
  102.   typename _Container::iterator iter;
  103. public:
  104.   typedef _Container          container_type;
  105.   typedef output_iterator_tag iterator_category;
  106.   typedef void                value_type;
  107.   typedef void                difference_type;
  108.   typedef void                pointer;
  109.   typedef void                reference;
  110.   insert_iterator(_Container& __x, typename _Container::iterator __i) 
  111.     : container(&__x), iter(__i) {}
  112.   insert_iterator<_Container>&
  113.   operator=(const typename _Container::value_type& __value) { 
  114.     iter = container->insert(iter, __value);
  115.     ++iter;
  116.     return *this;
  117.   }
  118.   insert_iterator<_Container>& operator*() { return *this; }
  119.   insert_iterator<_Container>& operator++() { return *this; }
  120.   insert_iterator<_Container>& operator++(int) { return *this; }
  121. };
  122. #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
  123. template <class _Container>
  124. inline output_iterator_tag
  125. iterator_category(const insert_iterator<_Container>&)
  126. {
  127.   return output_iterator_tag();
  128. }
  129. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  130. template <class _Container, class _Iterator>
  131. inline 
  132. insert_iterator<_Container> inserter(_Container& __x, _Iterator __i)
  133. {
  134.   typedef typename _Container::iterator __iter;
  135.   return insert_iterator<_Container>(__x, __iter(__i));
  136. }
  137. #ifndef __STL_LIMITED_DEFAULT_TEMPLATES
  138. template <class _BidirectionalIterator, class _Tp, class _Reference = _Tp&, 
  139.           class _Distance = ptrdiff_t> 
  140. #else
  141. template <class _BidirectionalIterator, class _Tp, class _Reference, 
  142.           class _Distance> 
  143. #endif
  144. class reverse_bidirectional_iterator {
  145.   typedef reverse_bidirectional_iterator<_BidirectionalIterator, _Tp, 
  146.                                          _Reference, _Distance>  _Self;
  147. protected:
  148.   _BidirectionalIterator current;
  149. public:
  150.   typedef bidirectional_iterator_tag iterator_category;
  151.   typedef _Tp                        value_type;
  152.   typedef _Distance                  difference_type;
  153.   typedef _Tp*                       pointer;
  154.   typedef _Reference                 reference;
  155.   reverse_bidirectional_iterator() {}
  156.   explicit reverse_bidirectional_iterator(_BidirectionalIterator __x)
  157.     : current(__x) {}
  158.   _BidirectionalIterator base() const { return current; }
  159.   _Reference operator*() const {
  160.     _BidirectionalIterator __tmp = current;
  161.     return *--__tmp;
  162.   }
  163. #ifndef __SGI_STL_NO_ARROW_OPERATOR
  164.   pointer operator->() const { return &(operator*()); }
  165. #endif /* __SGI_STL_NO_ARROW_OPERATOR */
  166.   _Self& operator++() {
  167.     --current;
  168.     return *this;
  169.   }
  170.   _Self operator++(int) {
  171.     _Self __tmp = *this;
  172.     --current;
  173.     return __tmp;
  174.   }
  175.   _Self& operator--() {
  176.     ++current;
  177.     return *this;
  178.   }
  179.   _Self operator--(int) {
  180.     _Self __tmp = *this;
  181.     ++current;
  182.     return __tmp;
  183.   }
  184. };
  185. #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
  186. template <class _BidirectionalIterator, class _Tp, class _Reference, 
  187.           class _Distance>
  188. inline bidirectional_iterator_tag
  189. iterator_category(const reverse_bidirectional_iterator<_BidirectionalIterator,
  190.                                                        _Tp, _Reference, 
  191.                                                        _Distance>&) 
  192. {
  193.   return bidirectional_iterator_tag();
  194. }
  195. template <class _BidirectionalIterator, class _Tp, class _Reference, 
  196.           class _Distance>
  197. inline _Tp*
  198. value_type(const reverse_bidirectional_iterator<_BidirectionalIterator, _Tp,
  199.                                                _Reference, _Distance>&)
  200. {
  201.   return (_Tp*) 0;
  202. }
  203. template <class _BidirectionalIterator, class _Tp, class _Reference, 
  204.           class _Distance>
  205. inline _Distance*
  206. distance_type(const reverse_bidirectional_iterator<_BidirectionalIterator, 
  207.                                                    _Tp,
  208.                                                    _Reference, _Distance>&)
  209. {
  210.   return (_Distance*) 0;
  211. }
  212. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  213. template <class _BiIter, class _Tp, class _Ref, class _Distance>
  214. inline bool operator==(
  215.     const reverse_bidirectional_iterator<_BiIter, _Tp, _Ref, _Distance>& __x, 
  216.     const reverse_bidirectional_iterator<_BiIter, _Tp, _Ref, _Distance>& __y)
  217. {
  218.   return __x.base() == __y.base();
  219. }
  220. #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER
  221. template <class _BiIter, class _Tp, class _Ref, class _Distance>
  222. inline bool operator!=(
  223.     const reverse_bidirectional_iterator<_BiIter, _Tp, _Ref, _Distance>& __x, 
  224.     const reverse_bidirectional_iterator<_BiIter, _Tp, _Ref, _Distance>& __y)
  225. {
  226.   return !(__x == __y);
  227. }
  228. #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */
  229. #ifdef __STL_CLASS_PARTIAL_SPECIALIZATION
  230. // This is the new version of reverse_iterator, as defined in the
  231. //  draft C++ standard.  It relies on the iterator_traits template,
  232. //  which in turn relies on partial specialization.  The class
  233. //  reverse_bidirectional_iterator is no longer part of the draft
  234. //  standard, but it is retained for backward compatibility.
  235. template <class _Iterator>
  236. class reverse_iterator 
  237. {
  238. protected:
  239.   _Iterator current;
  240. public:
  241.   typedef typename iterator_traits<_Iterator>::iterator_category
  242.           iterator_category;
  243.   typedef typename iterator_traits<_Iterator>::value_type
  244.           value_type;
  245.   typedef typename iterator_traits<_Iterator>::difference_type
  246.           difference_type;
  247.   typedef typename iterator_traits<_Iterator>::pointer
  248.           pointer;
  249.   typedef typename iterator_traits<_Iterator>::reference
  250.           reference;
  251.   typedef _Iterator iterator_type;
  252.   typedef reverse_iterator<_Iterator> _Self;
  253. public:
  254.   reverse_iterator() {}
  255.   explicit reverse_iterator(iterator_type __x) : current(__x) {}
  256.   reverse_iterator(const _Self& __x) : current(__x.current) {}
  257. #ifdef __STL_MEMBER_TEMPLATES
  258.   template <class _Iter>
  259.   reverse_iterator(const reverse_iterator<_Iter>& __x)
  260.     : current(__x.base()) {}
  261. #endif /* __STL_MEMBER_TEMPLATES */
  262.     
  263.   iterator_type base() const { return current; }
  264.   reference operator*() const {
  265.     _Iterator __tmp = current;
  266.     return *--__tmp;
  267.   }
  268. #ifndef __SGI_STL_NO_ARROW_OPERATOR
  269.   pointer operator->() const { return &(operator*()); }
  270. #endif /* __SGI_STL_NO_ARROW_OPERATOR */
  271.   _Self& operator++() {
  272.     --current;
  273.     return *this;
  274.   }
  275.   _Self operator++(int) {
  276.     _Self __tmp = *this;
  277.     --current;
  278.     return __tmp;
  279.   }
  280.   _Self& operator--() {
  281.     ++current;
  282.     return *this;
  283.   }
  284.   _Self operator--(int) {
  285.     _Self __tmp = *this;
  286.     ++current;
  287.     return __tmp;
  288.   }
  289.   _Self operator+(difference_type __n) const {
  290.     return _Self(current - __n);
  291.   }
  292.   _Self& operator+=(difference_type __n) {
  293.     current -= __n;
  294.     return *this;
  295.   }
  296.   _Self operator-(difference_type __n) const {
  297.     return _Self(current + __n);
  298.   }
  299.   _Self& operator-=(difference_type __n) {
  300.     current += __n;
  301.     return *this;
  302.   }
  303.   reference operator[](difference_type __n) const { return *(*this + __n); }  
  304. }; 
  305.  
  306. template <class _Iterator>
  307. inline bool operator==(const reverse_iterator<_Iterator>& __x, 
  308.                        const reverse_iterator<_Iterator>& __y) {
  309.   return __x.base() == __y.base();
  310. }
  311. template <class _Iterator>
  312. inline bool operator<(const reverse_iterator<_Iterator>& __x, 
  313.                       const reverse_iterator<_Iterator>& __y) {
  314.   return __y.base() < __x.base();
  315. }
  316. #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER
  317. template <class _Iterator>
  318. inline bool operator!=(const reverse_iterator<_Iterator>& __x, 
  319.                        const reverse_iterator<_Iterator>& __y) {
  320.   return !(__x == __y);
  321. }
  322. template <class _Iterator>
  323. inline bool operator>(const reverse_iterator<_Iterator>& __x, 
  324.                       const reverse_iterator<_Iterator>& __y) {
  325.   return __y < __x;
  326. }
  327. template <class _Iterator>
  328. inline bool operator<=(const reverse_iterator<_Iterator>& __x, 
  329.                        const reverse_iterator<_Iterator>& __y) {
  330.   return !(__y < __x);
  331. }
  332. template <class _Iterator>
  333. inline bool operator>=(const reverse_iterator<_Iterator>& __x, 
  334.                       const reverse_iterator<_Iterator>& __y) {
  335.   return !(__x < __y);
  336. }
  337. #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */
  338. template <class _Iterator>
  339. inline typename reverse_iterator<_Iterator>::difference_type
  340. operator-(const reverse_iterator<_Iterator>& __x, 
  341.           const reverse_iterator<_Iterator>& __y) {
  342.   return __y.base() - __x.base();
  343. }
  344. template <class _Iterator>
  345. inline reverse_iterator<_Iterator> 
  346. operator+(typename reverse_iterator<_Iterator>::difference_type __n,
  347.           const reverse_iterator<_Iterator>& __x) {
  348.   return reverse_iterator<_Iterator>(__x.base() - __n);
  349. }
  350. #else /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  351. // This is the old version of reverse_iterator, as found in the original
  352. //  HP STL.  It does not use partial specialization.
  353. #ifndef __STL_LIMITED_DEFAULT_TEMPLATES
  354. template <class _RandomAccessIterator, class _Tp, class _Reference = _Tp&,
  355.           class _Distance = ptrdiff_t> 
  356. #else
  357. template <class _RandomAccessIterator, class _Tp, class _Reference,
  358.           class _Distance> 
  359. #endif
  360. class reverse_iterator {
  361.   typedef reverse_iterator<_RandomAccessIterator, _Tp, _Reference, _Distance>
  362.         _Self;
  363. protected:
  364.   _RandomAccessIterator current;
  365. public:
  366.   typedef random_access_iterator_tag iterator_category;
  367.   typedef _Tp                        value_type;
  368.   typedef _Distance                  difference_type;
  369.   typedef _Tp*                       pointer;
  370.   typedef _Reference                 reference;
  371.   reverse_iterator() {}
  372.   explicit reverse_iterator(_RandomAccessIterator __x) : current(__x) {}
  373.   _RandomAccessIterator base() const { return current; }
  374.   _Reference operator*() const { return *(current - 1); }
  375. #ifndef __SGI_STL_NO_ARROW_OPERATOR
  376.   pointer operator->() const { return &(operator*()); }
  377. #endif /* __SGI_STL_NO_ARROW_OPERATOR */
  378.   _Self& operator++() {
  379.     --current;
  380.     return *this;
  381.   }
  382.   _Self operator++(int) {
  383.     _Self __tmp = *this;
  384.     --current;
  385.     return __tmp;
  386.   }
  387.   _Self& operator--() {
  388.     ++current;
  389.     return *this;
  390.   }
  391.   _Self operator--(int) {
  392.     _Self __tmp = *this;
  393.     ++current;
  394.     return __tmp;
  395.   }
  396.   _Self operator+(_Distance __n) const {
  397.     return _Self(current - __n);
  398.   }
  399.   _Self& operator+=(_Distance __n) {
  400.     current -= __n;
  401.     return *this;
  402.   }
  403.   _Self operator-(_Distance __n) const {
  404.     return _Self(current + __n);
  405.   }
  406.   _Self& operator-=(_Distance __n) {
  407.     current += __n;
  408.     return *this;
  409.   }
  410.   _Reference operator[](_Distance __n) const { return *(*this + __n); }
  411. };
  412. template <class _RandomAccessIterator, class _Tp, 
  413.           class _Reference, class _Distance>
  414. inline random_access_iterator_tag
  415. iterator_category(const reverse_iterator<_RandomAccessIterator, _Tp,
  416.                                          _Reference, _Distance>&)
  417. {
  418.   return random_access_iterator_tag();
  419. }
  420. template <class _RandomAccessIterator, class _Tp,
  421.           class _Reference, class _Distance>
  422. inline _Tp* value_type(const reverse_iterator<_RandomAccessIterator, _Tp,
  423.                                               _Reference, _Distance>&)
  424. {
  425.   return (_Tp*) 0;
  426. }
  427. template <class _RandomAccessIterator, class _Tp,
  428.           class _Reference, class _Distance>
  429. inline _Distance* 
  430. distance_type(const reverse_iterator<_RandomAccessIterator, 
  431.                                      _Tp, _Reference, _Distance>&)
  432. {
  433.   return (_Distance*) 0;
  434. }
  435. template <class _RandomAccessIterator, class _Tp,
  436.           class _Reference, class _Distance>
  437. inline bool 
  438. operator==(const reverse_iterator<_RandomAccessIterator, _Tp,
  439.                                   _Reference, _Distance>& __x, 
  440.            const reverse_iterator<_RandomAccessIterator, _Tp,
  441.                                   _Reference, _Distance>& __y)
  442. {
  443.   return __x.base() == __y.base();
  444. }
  445. template <class _RandomAccessIterator, class _Tp,
  446.           class _Reference, class _Distance>
  447. inline bool 
  448. operator<(const reverse_iterator<_RandomAccessIterator, _Tp,
  449.                                  _Reference, _Distance>& __x, 
  450.           const reverse_iterator<_RandomAccessIterator, _Tp,
  451.                                  _Reference, _Distance>& __y)
  452. {
  453.   return __y.base() < __x.base();
  454. }
  455. #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER
  456. template <class _RandomAccessIterator, class _Tp,
  457.           class _Reference, class _Distance>
  458. inline bool 
  459. operator!=(const reverse_iterator<_RandomAccessIterator, _Tp,
  460.                                   _Reference, _Distance>& __x, 
  461.            const reverse_iterator<_RandomAccessIterator, _Tp,
  462.                                   _Reference, _Distance>& __y) {
  463.   return !(__x == __y);
  464. }
  465. template <class _RandomAccessIterator, class _Tp,
  466.           class _Reference, class _Distance>
  467. inline bool 
  468. operator>(const reverse_iterator<_RandomAccessIterator, _Tp,
  469.                                  _Reference, _Distance>& __x, 
  470.           const reverse_iterator<_RandomAccessIterator, _Tp,
  471.                                  _Reference, _Distance>& __y) {
  472.   return __y < __x;
  473. }
  474. template <class _RandomAccessIterator, class _Tp,
  475.           class _Reference, class _Distance>
  476. inline bool 
  477. operator<=(const reverse_iterator<_RandomAccessIterator, _Tp,
  478.                                   _Reference, _Distance>& __x, 
  479.            const reverse_iterator<_RandomAccessIterator, _Tp,
  480.                                   _Reference, _Distance>& __y) {
  481.   return !(__y < __x);
  482. }
  483. template <class _RandomAccessIterator, class _Tp,
  484.           class _Reference, class _Distance>
  485. inline bool 
  486. operator>=(const reverse_iterator<_RandomAccessIterator, _Tp,
  487.                                   _Reference, _Distance>& __x, 
  488.            const reverse_iterator<_RandomAccessIterator, _Tp,
  489.                                   _Reference, _Distance>& __y) {
  490.   return !(__x < __y);
  491. }
  492. #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */
  493. template <class _RandomAccessIterator, class _Tp,
  494.           class _Reference, class _Distance>
  495. inline _Distance 
  496. operator-(const reverse_iterator<_RandomAccessIterator, _Tp,
  497.                                  _Reference, _Distance>& __x, 
  498.           const reverse_iterator<_RandomAccessIterator, _Tp,
  499.                                  _Reference, _Distance>& __y)
  500. {
  501.   return __y.base() - __x.base();
  502. }
  503. template <class _RandAccIter, class _Tp, class _Ref, class _Dist>
  504. inline reverse_iterator<_RandAccIter, _Tp, _Ref, _Dist> 
  505. operator+(_Dist __n,
  506.           const reverse_iterator<_RandAccIter, _Tp, _Ref, _Dist>& __x)
  507. {
  508.   return reverse_iterator<_RandAccIter, _Tp, _Ref, _Dist>(__x.base() - __n);
  509. }
  510. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  511. // istream_iterator and ostream_iterator look very different if we're
  512. // using new, templatized iostreams than if we're using the old cfront
  513. // version.
  514. #ifdef __STL_USE_NEW_IOSTREAMS
  515. template <class _Tp, 
  516.           class _CharT = char, class _Traits = char_traits<_CharT>,
  517.           class _Dist = ptrdiff_t> 
  518. class istream_iterator {
  519. public:
  520.   typedef _CharT                         char_type;
  521.   typedef _Traits                        traits_type;
  522.   typedef basic_istream<_CharT, _Traits> istream_type;
  523.   typedef input_iterator_tag             iterator_category;
  524.   typedef _Tp                            value_type;
  525.   typedef _Dist                          difference_type;
  526.   typedef const _Tp*                     pointer;
  527.   typedef const _Tp&                     reference;
  528.   istream_iterator() : _M_stream(0), _M_ok(false) {}
  529.   istream_iterator(istream_type& __s) : _M_stream(&__s) { _M_read(); }
  530.   reference operator*() const { return _M_value; }
  531.   pointer operator->() const { return &(operator*()); }
  532.   istream_iterator& operator++() { 
  533.     _M_read(); 
  534.     return *this;
  535.   }
  536.   istream_iterator operator++(int)  {
  537.     istream_iterator __tmp = *this;
  538.     _M_read();
  539.     return __tmp;
  540.   }
  541.   bool _M_equal(const istream_iterator& __x) const
  542.     { return (_M_ok == __x._M_ok) && (!_M_ok || _M_stream == __x._M_stream); }
  543. private:
  544.   istream_type* _M_stream;
  545.   _Tp _M_value;
  546.   bool _M_ok;
  547.   void _M_read() {
  548.     _M_ok = (_M_stream && *_M_stream) ? true : false;
  549.     if (_M_ok) {
  550.       *_M_stream >> _M_value;
  551.       _M_ok = *_M_stream ? true : false;
  552.     }
  553.   }
  554. };
  555. template <class _Tp, class _CharT, class _Traits, class _Dist>
  556. inline bool 
  557. operator==(const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __x,
  558.            const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __y) {
  559.   return __x._M_equal(__y);
  560. }
  561. #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER
  562. template <class _Tp, class _CharT, class _Traits, class _Dist>
  563. inline bool 
  564. operator!=(const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __x,
  565.            const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __y) {
  566.   return !__x._M_equal(__y);
  567. }
  568. #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */
  569. template <class _Tp,
  570.           class _CharT = char, class _Traits = char_traits<_CharT> >
  571. class ostream_iterator {
  572. public:
  573.   typedef _CharT                         char_type;
  574.   typedef _Traits                        traits_type;
  575.   typedef basic_ostream<_CharT, _Traits> ostream_type;
  576.   typedef output_iterator_tag            iterator_category;
  577.   typedef void                           value_type;
  578.   typedef void                           difference_type;
  579.   typedef void                           pointer;
  580.   typedef void                           reference;
  581.   ostream_iterator(ostream_type& __s) : _M_stream(&__s), _M_string(0) {}
  582.   ostream_iterator(ostream_type& __s, const _CharT* __c) 
  583.     : _M_stream(&__s), _M_string(__c)  {}
  584.   ostream_iterator<_Tp>& operator=(const _Tp& __value) { 
  585.     *_M_stream << __value;
  586.     if (_M_string) *_M_stream << _M_string;
  587.     return *this;
  588.   }
  589.   ostream_iterator<_Tp>& operator*() { return *this; }
  590.   ostream_iterator<_Tp>& operator++() { return *this; } 
  591.   ostream_iterator<_Tp>& operator++(int) { return *this; } 
  592. private:
  593.   ostream_type* _M_stream;
  594.   const _CharT* _M_string;
  595. };
  596. // The default template argument is declared in iosfwd
  597. // We do not read any characters until operator* is called.  The first
  598. // time operator* is called, it calls getc.  Subsequent calls to getc 
  599. // return a cached character, and calls to operator++ use snextc.  Before
  600. // operator* or operator++ has been called, _M_is_initialized is false.
  601. template<class _CharT, class _Traits>
  602. class istreambuf_iterator
  603.   : public iterator<input_iterator_tag, _CharT,
  604.                     typename _Traits::off_type, _CharT*, _CharT&>
  605. {
  606. public:
  607.   typedef _CharT                           char_type;
  608.   typedef _Traits                          traits_type;
  609.   typedef typename _Traits::int_type       int_type;
  610.   typedef basic_streambuf<_CharT, _Traits> streambuf_type;
  611.   typedef basic_istream<_CharT, _Traits>   istream_type;
  612. public:
  613.   istreambuf_iterator(streambuf_type* __p = 0) { this->_M_init(__p); }
  614.   istreambuf_iterator(istream_type& __is) { this->_M_init(__is.rdbuf()); }
  615.   char_type operator*() const 
  616.     { return _M_is_initialized ? _M_c : _M_dereference_aux(); }
  617.   istreambuf_iterator& operator++() { this->_M_nextc(); return *this; }
  618.   istreambuf_iterator  operator++(int) {
  619.     if (!_M_is_initialized)
  620.       _M_postincr_aux();
  621.     istreambuf_iterator __tmp = *this;
  622.     this->_M_nextc();
  623.     return __tmp;
  624.   }
  625.   bool equal(const istreambuf_iterator& __i) const {
  626.     return this->_M_is_initialized && __i._M_is_initialized
  627.       ? this->_M_eof == __i._M_eof
  628.       : this->_M_equal_aux(__i);
  629.   }
  630. private:
  631.   void _M_init(streambuf_type* __p) {
  632.     _M_buf = __p;
  633.     _M_eof = !__p;
  634.     _M_is_initialized = _M_eof;
  635.   }
  636.   char_type _M_dereference_aux() const;
  637.   bool _M_equal_aux(const istreambuf_iterator&) const;
  638.   void _M_postincr_aux();
  639.   void _M_nextc() {
  640.     int_type __c = _M_buf->snextc();
  641.     _M_c = traits_type::to_char_type(__c);    
  642.     _M_eof = traits_type::eq_int_type(__c, traits_type::eof());
  643.     _M_is_initialized = true;
  644.   }
  645.   void _M_getc() const {
  646.     int_type __c = _M_buf->sgetc();
  647.     _M_c = traits_type::to_char_type(__c);
  648.     _M_eof = traits_type::eq_int_type(__c, traits_type::eof());
  649.     _M_is_initialized = true;
  650.   }
  651. private:
  652.   streambuf_type* _M_buf;
  653.   mutable _CharT _M_c;
  654.   mutable bool _M_eof : 1;
  655.   mutable bool _M_is_initialized : 1;
  656. };
  657. template<class _CharT, class _Traits>
  658. _CharT istreambuf_iterator<_CharT, _Traits>::_M_dereference_aux() const
  659. {
  660.   this->_M_getc();
  661.   return _M_c;
  662. }
  663. template<class _CharT, class _Traits>
  664. bool istreambuf_iterator<_CharT, _Traits>
  665.   ::_M_equal_aux(const istreambuf_iterator& __i) const
  666. {
  667.   if (!this->_M_is_initialized)
  668.     this->_M_getc();
  669.   if (!__i._M_is_initialized)
  670.     __i._M_getc();
  671.   return this->_M_eof == __i._M_eof;
  672. }
  673. template<class _CharT, class _Traits>
  674. void istreambuf_iterator<_CharT, _Traits>::_M_postincr_aux()
  675. {
  676.   this->_M_getc();
  677. }
  678. template<class _CharT, class _Traits>
  679. inline bool operator==(const istreambuf_iterator<_CharT, _Traits>& __x,
  680.                        const istreambuf_iterator<_CharT, _Traits>& __y) {
  681.   return __x.equal(__y);
  682. }
  683. #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER
  684. template<class _CharT, class _Traits>
  685. inline bool operator!=(const istreambuf_iterator<_CharT, _Traits>& __x,
  686.                        const istreambuf_iterator<_CharT, _Traits>& __y) {
  687.   return !__x.equal(__y);
  688. }
  689. #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */
  690. // The default template argument is declared in iosfwd
  691. template<class _CharT, class _Traits>
  692. class ostreambuf_iterator
  693.   : public iterator<output_iterator_tag, void, void, void, void>
  694. {
  695. public:
  696.   typedef _CharT                           char_type;
  697.   typedef _Traits                          traits_type;
  698.   typedef typename _Traits::int_type       int_type;
  699.   typedef basic_streambuf<_CharT, _Traits> streambuf_type;
  700.   typedef basic_ostream<_CharT, _Traits>   ostream_type;
  701. public:
  702.   ostreambuf_iterator(streambuf_type* __buf) : _M_buf(__buf), _M_ok(__buf) {}
  703.   ostreambuf_iterator(ostream_type& __o)
  704.     : _M_buf(__o.rdbuf()), _M_ok(__o.rdbuf() != 0) {}
  705.   ostreambuf_iterator& operator=(char_type __c) {
  706.     _M_ok = _M_ok && !traits_type::eq_int_type(_M_buf->sputc(__c),
  707.                                                traits_type::eof());
  708.     return *this;
  709.   }    
  710.   
  711.   ostreambuf_iterator& operator*()     { return *this; }
  712.   ostreambuf_iterator& operator++()    { return *this; }
  713.   ostreambuf_iterator& operator++(int) { return *this; }
  714.   bool failed() const { return !_M_ok; }
  715. private:
  716.   streambuf_type* _M_buf;
  717.   bool _M_ok;
  718. };
  719. #else /* __STL_USE_NEW_IOSTREAMS */
  720. template <class _Tp, class _Dist = ptrdiff_t> class istream_iterator;
  721. template <class _Tp, class _Dist>
  722. inline bool operator==(const istream_iterator<_Tp, _Dist>&,
  723.                        const istream_iterator<_Tp, _Dist>&);
  724. template <class _Tp, class _Dist>
  725. class istream_iterator {
  726. #ifdef __STL_TEMPLATE_FRIENDS
  727.   template <class _T1, class _D1>
  728.   friend bool operator==(const istream_iterator<_T1, _D1>&,
  729.                          const istream_iterator<_T1, _D1>&);
  730. #else /* __STL_TEMPLATE_FRIENDS */
  731.   friend bool __STD_QUALIFIER
  732.   operator== __STL_NULL_TMPL_ARGS (const istream_iterator&,
  733.                                    const istream_iterator&);
  734. #endif /* __STL_TEMPLATE_FRIENDS */
  735. protected:
  736.   istream* _M_stream;
  737.   _Tp _M_value;
  738.   bool _M_end_marker;
  739.   void _M_read() {
  740.     _M_end_marker = (*_M_stream) ? true : false;
  741.     if (_M_end_marker) *_M_stream >> _M_value;
  742.     _M_end_marker = (*_M_stream) ? true : false;
  743.   }
  744. public:
  745.   typedef input_iterator_tag  iterator_category;
  746.   typedef _Tp                 value_type;
  747.   typedef _Dist               difference_type;
  748.   typedef const _Tp*          pointer;
  749.   typedef const _Tp&          reference;
  750.   istream_iterator() : _M_stream(&cin), _M_end_marker(false) {}
  751.   istream_iterator(istream& __s) : _M_stream(&__s) { _M_read(); }
  752.   reference operator*() const { return _M_value; }
  753. #ifndef __SGI_STL_NO_ARROW_OPERATOR
  754.   pointer operator->() const { return &(operator*()); }
  755. #endif /* __SGI_STL_NO_ARROW_OPERATOR */
  756.   istream_iterator<_Tp, _Dist>& operator++() { 
  757.     _M_read(); 
  758.     return *this;
  759.   }
  760.   istream_iterator<_Tp, _Dist> operator++(int)  {
  761.     istream_iterator<_Tp, _Dist> __tmp = *this;
  762.     _M_read();
  763.     return __tmp;
  764.   }
  765. };
  766. #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
  767. template <class _Tp, class _Dist>
  768. inline input_iterator_tag 
  769. iterator_category(const istream_iterator<_Tp, _Dist>&)
  770. {
  771.   return input_iterator_tag();
  772. }
  773. template <class _Tp, class _Dist>
  774. inline _Tp* 
  775. value_type(const istream_iterator<_Tp, _Dist>&) { return (_Tp*) 0; }
  776. template <class _Tp, class _Dist>
  777. inline _Dist* 
  778. distance_type(const istream_iterator<_Tp, _Dist>&) { return (_Dist*)0; }
  779. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  780. template <class _Tp, class _Distance>
  781. inline bool operator==(const istream_iterator<_Tp, _Distance>& __x,
  782.                        const istream_iterator<_Tp, _Distance>& __y) {
  783.   return (__x._M_stream == __y._M_stream &&
  784.           __x._M_end_marker == __y._M_end_marker) ||
  785.          __x._M_end_marker == false && __y._M_end_marker == false;
  786. }
  787. #ifdef __STL_FUNCTION_TMPL_PARTIAL_ORDER
  788. template <class _Tp, class _Distance>
  789. inline bool operator!=(const istream_iterator<_Tp, _Distance>& __x,
  790.                        const istream_iterator<_Tp, _Distance>& __y) {
  791.   return !(__x == __y);
  792. }
  793. #endif /* __STL_FUNCTION_TMPL_PARTIAL_ORDER */
  794. template <class _Tp>
  795. class ostream_iterator {
  796. protected:
  797.   ostream* _M_stream;
  798.   const char* _M_string;
  799. public:
  800.   typedef output_iterator_tag iterator_category;
  801.   typedef void                value_type;
  802.   typedef void                difference_type;
  803.   typedef void                pointer;
  804.   typedef void                reference;
  805.   ostream_iterator(ostream& __s) : _M_stream(&__s), _M_string(0) {}
  806.   ostream_iterator(ostream& __s, const char* __c) 
  807.     : _M_stream(&__s), _M_string(__c)  {}
  808.   ostream_iterator<_Tp>& operator=(const _Tp& __value) { 
  809.     *_M_stream << __value;
  810.     if (_M_string) *_M_stream << _M_string;
  811.     return *this;
  812.   }
  813.   ostream_iterator<_Tp>& operator*() { return *this; }
  814.   ostream_iterator<_Tp>& operator++() { return *this; } 
  815.   ostream_iterator<_Tp>& operator++(int) { return *this; } 
  816. };
  817. #ifndef __STL_CLASS_PARTIAL_SPECIALIZATION
  818. template <class _Tp>
  819. inline output_iterator_tag 
  820. iterator_category(const ostream_iterator<_Tp>&) {
  821.   return output_iterator_tag();
  822. }
  823. #endif /* __STL_CLASS_PARTIAL_SPECIALIZATION */
  824. #endif /* __STL_USE_NEW_IOSTREAMS */
  825. __STL_END_NAMESPACE
  826. #endif /* __SGI_STL_INTERNAL_ITERATOR_H */
  827. // Local Variables:
  828. // mode:C++
  829. // End: