stream_iterator.h revision 1.1.1.1.8.1
1// Stream iterators
2
3// Copyright (C) 2001-2013 Free Software Foundation, Inc.
4//
5// This file is part of the GNU ISO C++ Library.  This library is free
6// software; you can redistribute it and/or modify it under the
7// terms of the GNU General Public License as published by the
8// Free Software Foundation; either version 3, or (at your option)
9// any later version.
10
11// This library is distributed in the hope that it will be useful,
12// but WITHOUT ANY WARRANTY; without even the implied warranty of
13// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14// GNU General Public License for more details.
15
16// Under Section 7 of GPL version 3, you are granted additional
17// permissions described in the GCC Runtime Library Exception, version
18// 3.1, as published by the Free Software Foundation.
19
20// You should have received a copy of the GNU General Public License and
21// a copy of the GCC Runtime Library Exception along with this program;
22// see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
23// <http://www.gnu.org/licenses/>.
24
25/** @file bits/stream_iterator.h
26 *  This is an internal header file, included by other library headers.
27 *  Do not attempt to use it directly. @headername{iterator}
28 */
29
30#ifndef _STREAM_ITERATOR_H
31#define _STREAM_ITERATOR_H 1
32
33#pragma GCC system_header
34
35#include <debug/debug.h>
36
37namespace std _GLIBCXX_VISIBILITY(default)
38{
39_GLIBCXX_BEGIN_NAMESPACE_VERSION
40
41  /**
42   * @addtogroup iterators
43   * @{
44   */
45
46  /// Provides input iterator semantics for streams.
47  template<typename _Tp, typename _CharT = char,
48           typename _Traits = char_traits<_CharT>, typename _Dist = ptrdiff_t>
49    class istream_iterator
50    : public iterator<input_iterator_tag, _Tp, _Dist, const _Tp*, const _Tp&>
51    {
52    public:
53      typedef _CharT                         char_type;
54      typedef _Traits                        traits_type;
55      typedef basic_istream<_CharT, _Traits> istream_type;
56
57    private:
58      istream_type*	_M_stream;
59      _Tp		_M_value;
60      bool		_M_ok;
61
62    public:
63      ///  Construct end of input stream iterator.
64      _GLIBCXX_CONSTEXPR istream_iterator()
65      : _M_stream(0), _M_value(), _M_ok(false) {}
66
67      ///  Construct start of input stream iterator.
68      istream_iterator(istream_type& __s)
69      : _M_stream(&__s)
70      { _M_read(); }
71
72      istream_iterator(const istream_iterator& __obj)
73      : _M_stream(__obj._M_stream), _M_value(__obj._M_value),
74        _M_ok(__obj._M_ok)
75      { }
76
77      const _Tp&
78      operator*() const
79      {
80	__glibcxx_requires_cond(_M_ok,
81				_M_message(__gnu_debug::__msg_deref_istream)
82				._M_iterator(*this));
83	return _M_value;
84      }
85
86      const _Tp*
87      operator->() const { return &(operator*()); }
88
89      istream_iterator&
90      operator++()
91      {
92	__glibcxx_requires_cond(_M_ok,
93				_M_message(__gnu_debug::__msg_inc_istream)
94				._M_iterator(*this));
95	_M_read();
96	return *this;
97      }
98
99      istream_iterator
100      operator++(int)
101      {
102	__glibcxx_requires_cond(_M_ok,
103				_M_message(__gnu_debug::__msg_inc_istream)
104				._M_iterator(*this));
105	istream_iterator __tmp = *this;
106	_M_read();
107	return __tmp;
108      }
109
110      bool
111      _M_equal(const istream_iterator& __x) const
112      { return (_M_ok == __x._M_ok) && (!_M_ok || _M_stream == __x._M_stream); }
113
114    private:
115      void
116      _M_read()
117      {
118	_M_ok = (_M_stream && *_M_stream) ? true : false;
119	if (_M_ok)
120	  {
121	    *_M_stream >> _M_value;
122	    _M_ok = *_M_stream ? true : false;
123	  }
124      }
125    };
126
127  ///  Return true if x and y are both end or not end, or x and y are the same.
128  template<typename _Tp, typename _CharT, typename _Traits, typename _Dist>
129    inline bool
130    operator==(const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __x,
131	       const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __y)
132    { return __x._M_equal(__y); }
133
134  ///  Return false if x and y are both end or not end, or x and y are the same.
135  template <class _Tp, class _CharT, class _Traits, class _Dist>
136    inline bool
137    operator!=(const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __x,
138	       const istream_iterator<_Tp, _CharT, _Traits, _Dist>& __y)
139    { return !__x._M_equal(__y); }
140
141  /**
142   *  @brief  Provides output iterator semantics for streams.
143   *
144   *  This class provides an iterator to write to an ostream.  The type Tp is
145   *  the only type written by this iterator and there must be an
146   *  operator<<(Tp) defined.
147   *
148   *  @tparam  _Tp  The type to write to the ostream.
149   *  @tparam  _CharT  The ostream char_type.
150   *  @tparam  _Traits  The ostream char_traits.
151  */
152  template<typename _Tp, typename _CharT = char,
153           typename _Traits = char_traits<_CharT> >
154    class ostream_iterator
155    : public iterator<output_iterator_tag, void, void, void, void>
156    {
157    public:
158      //@{
159      /// Public typedef
160      typedef _CharT                         char_type;
161      typedef _Traits                        traits_type;
162      typedef basic_ostream<_CharT, _Traits> ostream_type;
163      //@}
164
165    private:
166      ostream_type*	_M_stream;
167      const _CharT*	_M_string;
168
169    public:
170      /// Construct from an ostream.
171      ostream_iterator(ostream_type& __s) : _M_stream(&__s), _M_string(0) {}
172
173      /**
174       *  Construct from an ostream.
175       *
176       *  The delimiter string @a c is written to the stream after every Tp
177       *  written to the stream.  The delimiter is not copied, and thus must
178       *  not be destroyed while this iterator is in use.
179       *
180       *  @param  __s  Underlying ostream to write to.
181       *  @param  __c  CharT delimiter string to insert.
182      */
183      ostream_iterator(ostream_type& __s, const _CharT* __c)
184      : _M_stream(&__s), _M_string(__c)  { }
185
186      /// Copy constructor.
187      ostream_iterator(const ostream_iterator& __obj)
188      : _M_stream(__obj._M_stream), _M_string(__obj._M_string)  { }
189
190      /// Writes @a value to underlying ostream using operator<<.  If
191      /// constructed with delimiter string, writes delimiter to ostream.
192      ostream_iterator&
193      operator=(const _Tp& __value)
194      {
195	__glibcxx_requires_cond(_M_stream != 0,
196				_M_message(__gnu_debug::__msg_output_ostream)
197				._M_iterator(*this));
198	*_M_stream << __value;
199	if (_M_string) *_M_stream << _M_string;
200	return *this;
201      }
202
203      ostream_iterator&
204      operator*()
205      { return *this; }
206
207      ostream_iterator&
208      operator++()
209      { return *this; }
210
211      ostream_iterator&
212      operator++(int)
213      { return *this; }
214    };
215
216  // @} group iterators
217
218_GLIBCXX_END_NAMESPACE_VERSION
219} // namespace
220
221#endif
222