]>
Commit | Line | Data |
---|---|---|
54c1bf78 | 1 | // String based streams -*- C++ -*- |
de96ac46 | 2 | |
fdeeef7f | 3 | // Copyright (C) 1997, 1998, 1999, 2002, 2003, 2004, 2005 |
26c691a8 | 4 | // Free Software Foundation, Inc. |
de96ac46 BK |
5 | // |
6 | // This file is part of the GNU ISO C++ Library. This library is free | |
7 | // software; you can redistribute it and/or modify it under the | |
8 | // terms of the GNU General Public License as published by the | |
9 | // Free Software Foundation; either version 2, or (at your option) | |
10 | // any later version. | |
11 | ||
12 | // This library is distributed in the hope that it will be useful, | |
13 | // but WITHOUT ANY WARRANTY; without even the implied warranty of | |
14 | // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
15 | // GNU General Public License for more details. | |
16 | ||
17 | // You should have received a copy of the GNU General Public License along | |
18 | // with this library; see the file COPYING. If not, write to the Free | |
83f51799 | 19 | // Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, |
de96ac46 BK |
20 | // USA. |
21 | ||
22 | // As a special exception, you may use this file as part of a free software | |
23 | // library without restriction. Specifically, if other files instantiate | |
24 | // templates or use macros or inline functions from this file, or you compile | |
25 | // this file and link it with other files to produce an executable, this | |
26 | // file does not by itself cause the resulting executable to be covered by | |
27 | // the GNU General Public License. This exception does not however | |
28 | // invalidate any other reasons why the executable file might be covered by | |
29 | // the GNU General Public License. | |
30 | ||
54c1bf78 BK |
31 | // |
32 | // ISO C++ 14882: 27.7 String-based streams | |
33 | // | |
34 | ||
ffe94f83 | 35 | /** @file sstream |
0aa06b18 | 36 | * This is a Standard C++ Library header. |
2f9d51b8 PE |
37 | */ |
38 | ||
1143680e SE |
39 | #ifndef _GLIBCXX_SSTREAM |
40 | #define _GLIBCXX_SSTREAM 1 | |
54c1bf78 BK |
41 | |
42 | #pragma GCC system_header | |
43 | ||
44 | #include <istream> | |
45 | #include <ostream> | |
46 | ||
3cbc7af0 BK |
47 | _GLIBCXX_BEGIN_NAMESPACE(std) |
48 | ||
840ceb34 PE |
49 | // [27.7.1] template class basic_stringbuf |
50 | /** | |
51 | * @brief The actual work of input and output (for std::string). | |
52 | * | |
53 | * This class associates either or both of its input and output sequences | |
54 | * with a sequence of characters, which can be initialized from, or made | |
55 | * available as, a @c std::basic_string. (Paraphrased from [27.7.1]/1.) | |
56 | * | |
57 | * For this class, open modes (of type @c ios_base::openmode) have | |
58 | * @c in set if the input sequence can be read, and @c out set if the | |
59 | * output sequence can be written. | |
60 | */ | |
54c1bf78 BK |
61 | template<typename _CharT, typename _Traits, typename _Alloc> |
62 | class basic_stringbuf : public basic_streambuf<_CharT, _Traits> | |
63 | { | |
64 | public: | |
65 | // Types: | |
66 | typedef _CharT char_type; | |
67 | typedef _Traits traits_type; | |
f5677b15 PC |
68 | // _GLIBCXX_RESOLVE_LIB_DEFECTS |
69 | // 251. basic_stringbuf missing allocator_type | |
54c1bf78 | 70 | typedef _Alloc allocator_type; |
54c1bf78 BK |
71 | typedef typename traits_type::int_type int_type; |
72 | typedef typename traits_type::pos_type pos_type; | |
73 | typedef typename traits_type::off_type off_type; | |
74 | ||
54c1bf78 BK |
75 | typedef basic_streambuf<char_type, traits_type> __streambuf_type; |
76 | typedef basic_string<char_type, _Traits, _Alloc> __string_type; | |
77 | typedef typename __string_type::size_type __size_type; | |
78 | ||
6f48900c | 79 | protected: |
cd16e04b PC |
80 | /** |
81 | * @if maint | |
82 | * Place to stash in || out || in | out settings for current stringbuf. | |
83 | * @endif | |
84 | */ | |
85 | ios_base::openmode _M_mode; | |
86 | ||
54c1bf78 BK |
87 | // Data Members: |
88 | __string_type _M_string; | |
798355a2 | 89 | |
54c1bf78 BK |
90 | public: |
91 | // Constructors: | |
840ceb34 PE |
92 | /** |
93 | * @brief Starts with an empty string buffer. | |
94 | * @param mode Whether the buffer can read, or write, or both. | |
95 | * | |
96 | * The default constructor initializes the parent class using its | |
97 | * own default ctor. | |
98 | */ | |
798355a2 | 99 | explicit |
54c1bf78 | 100 | basic_stringbuf(ios_base::openmode __mode = ios_base::in | ios_base::out) |
983de0da PC |
101 | : __streambuf_type(), _M_mode(__mode), _M_string() |
102 | { } | |
54c1bf78 | 103 | |
840ceb34 PE |
104 | /** |
105 | * @brief Starts with an existing string buffer. | |
106 | * @param str A string to copy as a starting buffer. | |
107 | * @param mode Whether the buffer can read, or write, or both. | |
108 | * | |
109 | * This constructor initializes the parent class using its | |
110 | * own default ctor. | |
111 | */ | |
798355a2 | 112 | explicit |
54c1bf78 BK |
113 | basic_stringbuf(const __string_type& __str, |
114 | ios_base::openmode __mode = ios_base::in | ios_base::out) | |
26c691a8 | 115 | : __streambuf_type(), _M_mode(), _M_string(__str.data(), __str.size()) |
54c1bf78 BK |
116 | { _M_stringbuf_init(__mode); } |
117 | ||
118 | // Get and set: | |
840ceb34 PE |
119 | /** |
120 | * @brief Copying out the string buffer. | |
121 | * @return A copy of one of the underlying sequences. | |
122 | * | |
123 | * "If the buffer is only created in input mode, the underlying | |
124 | * character sequence is equal to the input sequence; otherwise, it | |
125 | * is equal to the output sequence." [27.7.1.2]/1 | |
126 | */ | |
798355a2 PE |
127 | __string_type |
128 | str() const | |
54c1bf78 | 129 | { |
fdeeef7f | 130 | __string_type __ret; |
983de0da | 131 | if (this->pptr()) |
1b170b55 PC |
132 | { |
133 | // The current egptr() may not be the actual string end. | |
134 | if (this->pptr() > this->egptr()) | |
fdeeef7f | 135 | __ret = __string_type(this->pbase(), this->pptr()); |
1b170b55 | 136 | else |
fdeeef7f | 137 | __ret = __string_type(this->pbase(), this->egptr()); |
1b170b55 PC |
138 | } |
139 | else | |
fdeeef7f BK |
140 | __ret = _M_string; |
141 | return __ret; | |
54c1bf78 BK |
142 | } |
143 | ||
840ceb34 PE |
144 | /** |
145 | * @brief Setting a new buffer. | |
146 | * @param s The string to use as a new sequence. | |
147 | * | |
148 | * Deallocates any previous stored sequence, then copies @a s to | |
149 | * use as a new one. | |
150 | */ | |
798355a2 | 151 | void |
54c1bf78 BK |
152 | str(const __string_type& __s) |
153 | { | |
81646a31 | 154 | // Cannot use _M_string = __s, since v3 strings are COW. |
93d87ec6 | 155 | _M_string.assign(__s.data(), __s.size()); |
fdeeef7f | 156 | _M_stringbuf_init(_M_mode); |
54c1bf78 BK |
157 | } |
158 | ||
159 | protected: | |
983de0da | 160 | // Common initialization code goes here. |
54c1bf78 BK |
161 | void |
162 | _M_stringbuf_init(ios_base::openmode __mode) | |
163 | { | |
fdeeef7f | 164 | _M_mode = __mode; |
23cac885 | 165 | __size_type __len = 0; |
fdeeef7f | 166 | if (_M_mode & (ios_base::ate | ios_base::app)) |
23cac885 | 167 | __len = _M_string.size(); |
655d7821 | 168 | _M_sync(const_cast<char_type*>(_M_string.data()), 0, __len); |
54c1bf78 BK |
169 | } |
170 | ||
fdeeef7f BK |
171 | virtual streamsize |
172 | showmanyc() | |
173 | { | |
174 | streamsize __ret = -1; | |
175 | if (_M_mode & ios_base::in) | |
176 | { | |
177 | _M_update_egptr(); | |
178 | __ret = this->egptr() - this->gptr(); | |
179 | } | |
180 | return __ret; | |
181 | } | |
182 | ||
1b170b55 | 183 | virtual int_type |
cd16e04b | 184 | underflow(); |
54c1bf78 | 185 | |
798355a2 | 186 | virtual int_type |
54c1bf78 BK |
187 | pbackfail(int_type __c = traits_type::eof()); |
188 | ||
798355a2 | 189 | virtual int_type |
54c1bf78 BK |
190 | overflow(int_type __c = traits_type::eof()); |
191 | ||
840ceb34 PE |
192 | /** |
193 | * @brief Manipulates the buffer. | |
194 | * @param s Pointer to a buffer area. | |
195 | * @param n Size of @a s. | |
196 | * @return @c this | |
197 | * | |
198 | * If no buffer has already been created, and both @a s and @a n are | |
199 | * non-zero, then @c s is used as a buffer; see | |
200 | * http://gcc.gnu.org/onlinedocs/libstdc++/27_io/howto.html#2 | |
201 | * for more. | |
202 | */ | |
798355a2 | 203 | virtual __streambuf_type* |
54c1bf78 | 204 | setbuf(char_type* __s, streamsize __n) |
798355a2 | 205 | { |
b82a33d2 | 206 | if (__s && __n >= 0) |
54c1bf78 | 207 | { |
23cac885 | 208 | // This is implementation-defined behavior, and assumes |
b82a33d2 PC |
209 | // that an external char_type array of length __n exists |
210 | // and has been pre-allocated. If this is not the case, | |
211 | // things will quickly blow up. | |
23cac885 BK |
212 | |
213 | // Step 1: Destroy the current internal array. | |
f67b6b7a | 214 | _M_string.assign(__s, __n); |
23cac885 BK |
215 | |
216 | // Step 2: Use the external array. | |
655d7821 | 217 | _M_sync(__s, 0, 0); |
54c1bf78 | 218 | } |
798355a2 PE |
219 | return this; |
220 | } | |
54c1bf78 | 221 | |
798355a2 | 222 | virtual pos_type |
54c1bf78 BK |
223 | seekoff(off_type __off, ios_base::seekdir __way, |
224 | ios_base::openmode __mode = ios_base::in | ios_base::out); | |
225 | ||
798355a2 PE |
226 | virtual pos_type |
227 | seekpos(pos_type __sp, | |
54c1bf78 BK |
228 | ios_base::openmode __mode = ios_base::in | ios_base::out); |
229 | ||
230 | // Internal function for correctly updating the internal buffer | |
231 | // for a particular _M_string, due to initialization or | |
232 | // re-sizing of an existing _M_string. | |
233 | // Assumes: contents of _M_string and internal buffer match exactly. | |
798355a2 | 234 | // __i == _M_in_cur - _M_in_beg |
54c1bf78 | 235 | // __o == _M_out_cur - _M_out_beg |
50af15ec | 236 | void |
655d7821 | 237 | _M_sync(char_type* __base, __size_type __i, __size_type __o) |
54c1bf78 | 238 | { |
fdeeef7f BK |
239 | const bool __testin = _M_mode & ios_base::in; |
240 | const bool __testout = _M_mode & ios_base::out; | |
f67b6b7a | 241 | char_type* __end = __base + _M_string.size(); |
54c1bf78 | 242 | |
54c1bf78 | 243 | if (__testin) |
f67b6b7a | 244 | this->setg(__base, __base + __i, __end); |
54c1bf78 BK |
245 | if (__testout) |
246 | { | |
dbb8bfe8 PC |
247 | // If __base comes from setbuf we cannot trust capacity() |
248 | // to match the size of the buffer area: in general, after | |
249 | // Step 1 above, _M_string.capacity() >= __n. | |
250 | if (__base == _M_string.data()) | |
251 | this->setp(__base, __base + _M_string.capacity()); | |
252 | else | |
253 | this->setp(__base, __end); | |
1b170b55 | 254 | this->pbump(__o); |
f67b6b7a PC |
255 | // egptr() always tracks the string end. When !__testin, |
256 | // for the correct functioning of the streambuf inlines | |
257 | // the other get area pointers are identical. | |
1b170b55 | 258 | if (!__testin) |
f67b6b7a | 259 | this->setg(__end, __end, __end); |
54c1bf78 | 260 | } |
54c1bf78 | 261 | } |
1b170b55 PC |
262 | |
263 | // Internal function for correctly updating egptr() to the actual | |
264 | // string end. | |
265 | void | |
266 | _M_update_egptr() | |
267 | { | |
fdeeef7f | 268 | const bool __testin = _M_mode & ios_base::in; |
983de0da | 269 | if (this->pptr() && this->pptr() > this->egptr()) |
1b170b55 PC |
270 | if (__testin) |
271 | this->setg(this->eback(), this->gptr(), this->pptr()); | |
272 | else | |
273 | this->setg(this->pptr(), this->pptr(), this->pptr()); | |
274 | } | |
54c1bf78 BK |
275 | }; |
276 | ||
277 | ||
840ceb34 PE |
278 | // [27.7.2] Template class basic_istringstream |
279 | /** | |
280 | * @brief Controlling input for std::string. | |
281 | * | |
282 | * This class supports reading from objects of type std::basic_string, | |
283 | * using the inherited functions from std::basic_istream. To control | |
284 | * the associated sequence, an instance of std::basic_stringbuf is used, | |
285 | * which this page refers to as @c sb. | |
286 | */ | |
54c1bf78 BK |
287 | template<typename _CharT, typename _Traits, typename _Alloc> |
288 | class basic_istringstream : public basic_istream<_CharT, _Traits> | |
289 | { | |
290 | public: | |
291 | // Types: | |
292 | typedef _CharT char_type; | |
293 | typedef _Traits traits_type; | |
f5677b15 PC |
294 | // _GLIBCXX_RESOLVE_LIB_DEFECTS |
295 | // 251. basic_stringbuf missing allocator_type | |
54c1bf78 | 296 | typedef _Alloc allocator_type; |
54c1bf78 BK |
297 | typedef typename traits_type::int_type int_type; |
298 | typedef typename traits_type::pos_type pos_type; | |
299 | typedef typename traits_type::off_type off_type; | |
300 | ||
301 | // Non-standard types: | |
302 | typedef basic_string<_CharT, _Traits, _Alloc> __string_type; | |
303 | typedef basic_stringbuf<_CharT, _Traits, _Alloc> __stringbuf_type; | |
304 | typedef basic_istream<char_type, traits_type> __istream_type; | |
305 | ||
306 | private: | |
307 | __stringbuf_type _M_stringbuf; | |
308 | ||
309 | public: | |
310 | // Constructors: | |
840ceb34 PE |
311 | /** |
312 | * @brief Default constructor starts with an empty string buffer. | |
313 | * @param mode Whether the buffer can read, or write, or both. | |
314 | * | |
315 | * @c ios_base::in is automatically included in @a mode. | |
316 | * | |
317 | * Initializes @c sb using @c mode|in, and passes @c &sb to the base | |
318 | * class initializer. Does not allocate any buffer. | |
319 | * | |
320 | * @if maint | |
321 | * That's a lie. We initialize the base class with NULL, because the | |
322 | * string class does its own memory management. | |
323 | * @endif | |
324 | */ | |
798355a2 | 325 | explicit |
54c1bf78 | 326 | basic_istringstream(ios_base::openmode __mode = ios_base::in) |
d29cc32f | 327 | : __istream_type(), _M_stringbuf(__mode | ios_base::in) |
54c1bf78 BK |
328 | { this->init(&_M_stringbuf); } |
329 | ||
840ceb34 PE |
330 | /** |
331 | * @brief Starts with an existing string buffer. | |
332 | * @param str A string to copy as a starting buffer. | |
333 | * @param mode Whether the buffer can read, or write, or both. | |
334 | * | |
335 | * @c ios_base::in is automatically included in @a mode. | |
336 | * | |
337 | * Initializes @c sb using @a str and @c mode|in, and passes @c &sb | |
338 | * to the base class initializer. | |
339 | * | |
340 | * @if maint | |
341 | * That's a lie. We initialize the base class with NULL, because the | |
342 | * string class does its own memory management. | |
343 | * @endif | |
344 | */ | |
798355a2 | 345 | explicit |
54c1bf78 BK |
346 | basic_istringstream(const __string_type& __str, |
347 | ios_base::openmode __mode = ios_base::in) | |
d29cc32f | 348 | : __istream_type(), _M_stringbuf(__str, __mode | ios_base::in) |
54c1bf78 BK |
349 | { this->init(&_M_stringbuf); } |
350 | ||
840ceb34 PE |
351 | /** |
352 | * @brief The destructor does nothing. | |
353 | * | |
354 | * The buffer is deallocated by the stringbuf object, not the | |
355 | * formatting stream. | |
356 | */ | |
54c1bf78 BK |
357 | ~basic_istringstream() |
358 | { } | |
359 | ||
360 | // Members: | |
840ceb34 PE |
361 | /** |
362 | * @brief Accessing the underlying buffer. | |
363 | * @return The current basic_stringbuf buffer. | |
364 | * | |
365 | * This hides both signatures of std::basic_ios::rdbuf(). | |
366 | */ | |
798355a2 | 367 | __stringbuf_type* |
54c1bf78 BK |
368 | rdbuf() const |
369 | { return const_cast<__stringbuf_type*>(&_M_stringbuf); } | |
370 | ||
840ceb34 PE |
371 | /** |
372 | * @brief Copying out the string buffer. | |
373 | * @return @c rdbuf()->str() | |
374 | */ | |
54c1bf78 BK |
375 | __string_type |
376 | str() const | |
377 | { return _M_stringbuf.str(); } | |
798355a2 | 378 | |
840ceb34 PE |
379 | /** |
380 | * @brief Setting a new buffer. | |
381 | * @param s The string to use as a new sequence. | |
382 | * | |
383 | * Calls @c rdbuf()->str(s). | |
384 | */ | |
798355a2 | 385 | void |
54c1bf78 BK |
386 | str(const __string_type& __s) |
387 | { _M_stringbuf.str(__s); } | |
388 | }; | |
389 | ||
390 | ||
840ceb34 PE |
391 | // [27.7.3] Template class basic_ostringstream |
392 | /** | |
393 | * @brief Controlling output for std::string. | |
394 | * | |
395 | * This class supports writing to objects of type std::basic_string, | |
396 | * using the inherited functions from std::basic_ostream. To control | |
397 | * the associated sequence, an instance of std::basic_stringbuf is used, | |
398 | * which this page refers to as @c sb. | |
399 | */ | |
54c1bf78 BK |
400 | template <typename _CharT, typename _Traits, typename _Alloc> |
401 | class basic_ostringstream : public basic_ostream<_CharT, _Traits> | |
402 | { | |
403 | public: | |
404 | // Types: | |
405 | typedef _CharT char_type; | |
406 | typedef _Traits traits_type; | |
f5677b15 PC |
407 | // _GLIBCXX_RESOLVE_LIB_DEFECTS |
408 | // 251. basic_stringbuf missing allocator_type | |
54c1bf78 | 409 | typedef _Alloc allocator_type; |
54c1bf78 BK |
410 | typedef typename traits_type::int_type int_type; |
411 | typedef typename traits_type::pos_type pos_type; | |
412 | typedef typename traits_type::off_type off_type; | |
413 | ||
414 | // Non-standard types: | |
415 | typedef basic_string<_CharT, _Traits, _Alloc> __string_type; | |
416 | typedef basic_stringbuf<_CharT, _Traits, _Alloc> __stringbuf_type; | |
417 | typedef basic_ostream<char_type, traits_type> __ostream_type; | |
418 | ||
419 | private: | |
420 | __stringbuf_type _M_stringbuf; | |
421 | ||
422 | public: | |
840ceb34 PE |
423 | // Constructors/destructor: |
424 | /** | |
425 | * @brief Default constructor starts with an empty string buffer. | |
426 | * @param mode Whether the buffer can read, or write, or both. | |
427 | * | |
428 | * @c ios_base::out is automatically included in @a mode. | |
429 | * | |
430 | * Initializes @c sb using @c mode|out, and passes @c &sb to the base | |
431 | * class initializer. Does not allocate any buffer. | |
432 | * | |
433 | * @if maint | |
434 | * That's a lie. We initialize the base class with NULL, because the | |
435 | * string class does its own memory management. | |
436 | * @endif | |
437 | */ | |
798355a2 | 438 | explicit |
54c1bf78 | 439 | basic_ostringstream(ios_base::openmode __mode = ios_base::out) |
d29cc32f | 440 | : __ostream_type(), _M_stringbuf(__mode | ios_base::out) |
54c1bf78 BK |
441 | { this->init(&_M_stringbuf); } |
442 | ||
840ceb34 PE |
443 | /** |
444 | * @brief Starts with an existing string buffer. | |
445 | * @param str A string to copy as a starting buffer. | |
446 | * @param mode Whether the buffer can read, or write, or both. | |
447 | * | |
448 | * @c ios_base::out is automatically included in @a mode. | |
449 | * | |
450 | * Initializes @c sb using @a str and @c mode|out, and passes @c &sb | |
451 | * to the base class initializer. | |
452 | * | |
453 | * @if maint | |
454 | * That's a lie. We initialize the base class with NULL, because the | |
455 | * string class does its own memory management. | |
456 | * @endif | |
457 | */ | |
798355a2 | 458 | explicit |
54c1bf78 BK |
459 | basic_ostringstream(const __string_type& __str, |
460 | ios_base::openmode __mode = ios_base::out) | |
d29cc32f | 461 | : __ostream_type(), _M_stringbuf(__str, __mode | ios_base::out) |
54c1bf78 BK |
462 | { this->init(&_M_stringbuf); } |
463 | ||
840ceb34 PE |
464 | /** |
465 | * @brief The destructor does nothing. | |
466 | * | |
467 | * The buffer is deallocated by the stringbuf object, not the | |
468 | * formatting stream. | |
469 | */ | |
54c1bf78 BK |
470 | ~basic_ostringstream() |
471 | { } | |
472 | ||
473 | // Members: | |
840ceb34 PE |
474 | /** |
475 | * @brief Accessing the underlying buffer. | |
476 | * @return The current basic_stringbuf buffer. | |
477 | * | |
478 | * This hides both signatures of std::basic_ios::rdbuf(). | |
479 | */ | |
798355a2 | 480 | __stringbuf_type* |
54c1bf78 BK |
481 | rdbuf() const |
482 | { return const_cast<__stringbuf_type*>(&_M_stringbuf); } | |
483 | ||
840ceb34 PE |
484 | /** |
485 | * @brief Copying out the string buffer. | |
486 | * @return @c rdbuf()->str() | |
487 | */ | |
54c1bf78 BK |
488 | __string_type |
489 | str() const | |
490 | { return _M_stringbuf.str(); } | |
798355a2 | 491 | |
840ceb34 PE |
492 | /** |
493 | * @brief Setting a new buffer. | |
494 | * @param s The string to use as a new sequence. | |
495 | * | |
496 | * Calls @c rdbuf()->str(s). | |
497 | */ | |
798355a2 | 498 | void |
54c1bf78 BK |
499 | str(const __string_type& __s) |
500 | { _M_stringbuf.str(__s); } | |
501 | }; | |
798355a2 PE |
502 | |
503 | ||
840ceb34 PE |
504 | // [27.7.4] Template class basic_stringstream |
505 | /** | |
506 | * @brief Controlling input and output for std::string. | |
507 | * | |
508 | * This class supports reading from and writing to objects of type | |
509 | * std::basic_string, using the inherited functions from | |
510 | * std::basic_iostream. To control the associated sequence, an instance | |
511 | * of std::basic_stringbuf is used, which this page refers to as @c sb. | |
512 | */ | |
54c1bf78 BK |
513 | template <typename _CharT, typename _Traits, typename _Alloc> |
514 | class basic_stringstream : public basic_iostream<_CharT, _Traits> | |
515 | { | |
516 | public: | |
517 | // Types: | |
518 | typedef _CharT char_type; | |
519 | typedef _Traits traits_type; | |
f5677b15 PC |
520 | // _GLIBCXX_RESOLVE_LIB_DEFECTS |
521 | // 251. basic_stringbuf missing allocator_type | |
54c1bf78 | 522 | typedef _Alloc allocator_type; |
54c1bf78 BK |
523 | typedef typename traits_type::int_type int_type; |
524 | typedef typename traits_type::pos_type pos_type; | |
525 | typedef typename traits_type::off_type off_type; | |
526 | ||
527 | // Non-standard Types: | |
528 | typedef basic_string<_CharT, _Traits, _Alloc> __string_type; | |
529 | typedef basic_stringbuf<_CharT, _Traits, _Alloc> __stringbuf_type; | |
530 | typedef basic_iostream<char_type, traits_type> __iostream_type; | |
531 | ||
532 | private: | |
533 | __stringbuf_type _M_stringbuf; | |
534 | ||
535 | public: | |
536 | // Constructors/destructors | |
840ceb34 PE |
537 | /** |
538 | * @brief Default constructor starts with an empty string buffer. | |
539 | * @param mode Whether the buffer can read, or write, or both. | |
540 | * | |
541 | * Initializes @c sb using @c mode, and passes @c &sb to the base | |
542 | * class initializer. Does not allocate any buffer. | |
543 | * | |
544 | * @if maint | |
545 | * That's a lie. We initialize the base class with NULL, because the | |
546 | * string class does its own memory management. | |
547 | * @endif | |
548 | */ | |
798355a2 | 549 | explicit |
54c1bf78 | 550 | basic_stringstream(ios_base::openmode __m = ios_base::out | ios_base::in) |
d29cc32f | 551 | : __iostream_type(), _M_stringbuf(__m) |
54c1bf78 BK |
552 | { this->init(&_M_stringbuf); } |
553 | ||
840ceb34 PE |
554 | /** |
555 | * @brief Starts with an existing string buffer. | |
556 | * @param str A string to copy as a starting buffer. | |
557 | * @param mode Whether the buffer can read, or write, or both. | |
558 | * | |
559 | * Initializes @c sb using @a str and @c mode, and passes @c &sb | |
560 | * to the base class initializer. | |
561 | * | |
562 | * @if maint | |
563 | * That's a lie. We initialize the base class with NULL, because the | |
564 | * string class does its own memory management. | |
565 | * @endif | |
566 | */ | |
798355a2 | 567 | explicit |
54c1bf78 BK |
568 | basic_stringstream(const __string_type& __str, |
569 | ios_base::openmode __m = ios_base::out | ios_base::in) | |
d29cc32f | 570 | : __iostream_type(), _M_stringbuf(__str, __m) |
54c1bf78 BK |
571 | { this->init(&_M_stringbuf); } |
572 | ||
840ceb34 PE |
573 | /** |
574 | * @brief The destructor does nothing. | |
575 | * | |
576 | * The buffer is deallocated by the stringbuf object, not the | |
577 | * formatting stream. | |
578 | */ | |
54c1bf78 BK |
579 | ~basic_stringstream() |
580 | { } | |
581 | ||
582 | // Members: | |
840ceb34 PE |
583 | /** |
584 | * @brief Accessing the underlying buffer. | |
585 | * @return The current basic_stringbuf buffer. | |
586 | * | |
587 | * This hides both signatures of std::basic_ios::rdbuf(). | |
588 | */ | |
798355a2 | 589 | __stringbuf_type* |
54c1bf78 BK |
590 | rdbuf() const |
591 | { return const_cast<__stringbuf_type*>(&_M_stringbuf); } | |
592 | ||
840ceb34 PE |
593 | /** |
594 | * @brief Copying out the string buffer. | |
595 | * @return @c rdbuf()->str() | |
596 | */ | |
54c1bf78 BK |
597 | __string_type |
598 | str() const | |
599 | { return _M_stringbuf.str(); } | |
600 | ||
840ceb34 PE |
601 | /** |
602 | * @brief Setting a new buffer. | |
603 | * @param s The string to use as a new sequence. | |
604 | * | |
605 | * Calls @c rdbuf()->str(s). | |
606 | */ | |
798355a2 | 607 | void |
54c1bf78 BK |
608 | str(const __string_type& __s) |
609 | { _M_stringbuf.str(__s); } | |
610 | }; | |
3cbc7af0 BK |
611 | |
612 | _GLIBCXX_END_NAMESPACE | |
54c1bf78 | 613 | |
5f697f7a | 614 | #ifndef _GLIBCXX_EXPORT_TEMPLATE |
54c1bf78 BK |
615 | # include <bits/sstream.tcc> |
616 | #endif | |
54c1bf78 | 617 | |
1143680e | 618 | #endif /* _GLIBCXX_SSTREAM */ |