00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041 #ifndef _CPP_BITS_STRING_TCC
00042 #define _CPP_BITS_STRING_TCC 1
00043
00044 #pragma GCC system_header
00045
00046 namespace std
00047 {
00048 template<typename _CharT, typename _Traits, typename _Alloc>
00049 const typename basic_string<_CharT, _Traits, _Alloc>::size_type
00050 basic_string<_CharT, _Traits, _Alloc>::
00051 _Rep::_S_max_size = (((npos - sizeof(_Rep))/sizeof(_CharT)) - 1) / 4;
00052
00053 template<typename _CharT, typename _Traits, typename _Alloc>
00054 const _CharT
00055 basic_string<_CharT, _Traits, _Alloc>::
00056 _Rep::_S_terminal = _CharT();
00057
00058 template<typename _CharT, typename _Traits, typename _Alloc>
00059 const typename basic_string<_CharT, _Traits, _Alloc>::size_type
00060 basic_string<_CharT, _Traits, _Alloc>::npos;
00061
00062
00063
00064 template<typename _CharT, typename _Traits, typename _Alloc>
00065 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00066 basic_string<_CharT, _Traits, _Alloc>::_S_empty_rep_storage[
00067 (sizeof(_Rep) + sizeof(_CharT) + sizeof(size_type) - 1)/sizeof(size_type)];
00068
00069
00070
00071
00072
00073 template<typename _CharT, typename _Traits, typename _Alloc>
00074 template<typename _InIter>
00075 _CharT*
00076 basic_string<_CharT, _Traits, _Alloc>::
00077 _S_construct(_InIter __beg, _InIter __end, const _Alloc& __a,
00078 input_iterator_tag)
00079 {
00080 if (__beg == __end && __a == _Alloc())
00081 return _S_empty_rep()._M_refcopy();
00082
00083 _CharT __buf[100];
00084 size_type __i = 0;
00085 while (__beg != __end && __i < sizeof(__buf) / sizeof(_CharT))
00086 {
00087 __buf[__i++] = *__beg;
00088 ++__beg;
00089 }
00090 _Rep* __r = _Rep::_S_create(__i, __a);
00091 traits_type::copy(__r->_M_refdata(), __buf, __i);
00092 __r->_M_length = __i;
00093 try
00094 {
00095
00096
00097
00098 for (;;)
00099 {
00100 _CharT* __p = __r->_M_refdata() + __r->_M_length;
00101 _CharT* __last = __r->_M_refdata() + __r->_M_capacity;
00102 for (;;)
00103 {
00104 if (__beg == __end)
00105 {
00106 __r->_M_length = __p - __r->_M_refdata();
00107 *__p = _Rep::_S_terminal;
00108 return __r->_M_refdata();
00109 }
00110 if (__p == __last)
00111 break;
00112 *__p++ = *__beg;
00113 ++__beg;
00114 }
00115
00116 size_type __len = __p - __r->_M_refdata();
00117 _Rep* __another = _Rep::_S_create(__len + 1, __a);
00118 traits_type::copy(__another->_M_refdata(),
00119 __r->_M_refdata(), __len);
00120 __r->_M_destroy(__a);
00121 __r = __another;
00122 __r->_M_length = __len;
00123 }
00124 }
00125 catch(...)
00126 {
00127 __r->_M_destroy(__a);
00128 __throw_exception_again;
00129 }
00130 return 0;
00131 }
00132
00133 template<typename _CharT, typename _Traits, typename _Alloc>
00134 template <class _InIter>
00135 _CharT*
00136 basic_string<_CharT, _Traits, _Alloc>::
00137 _S_construct(_InIter __beg, _InIter __end, const _Alloc& __a,
00138 forward_iterator_tag)
00139 {
00140 if (__beg == __end && __a == _Alloc())
00141 return _S_empty_rep()._M_refcopy();
00142
00143
00144 if (__builtin_expect(__beg == _InIter(), 0))
00145 __throw_logic_error("attempt to create string with null pointer");
00146
00147 size_type __dnew = static_cast<size_type>(std::distance(__beg, __end));
00148
00149
00150 _Rep* __r = _Rep::_S_create(__dnew, __a);
00151 try
00152 { _S_copy_chars(__r->_M_refdata(), __beg, __end); }
00153 catch(...)
00154 {
00155 __r->_M_destroy(__a);
00156 __throw_exception_again;
00157 }
00158 __r->_M_length = __dnew;
00159
00160 __r->_M_refdata()[__dnew] = _Rep::_S_terminal;
00161 return __r->_M_refdata();
00162 }
00163
00164 template<typename _CharT, typename _Traits, typename _Alloc>
00165 _CharT*
00166 basic_string<_CharT, _Traits, _Alloc>::
00167 _S_construct(size_type __n, _CharT __c, const _Alloc& __a)
00168 {
00169 if (__n == 0 && __a == _Alloc())
00170 return _S_empty_rep()._M_refcopy();
00171
00172
00173 _Rep* __r = _Rep::_S_create(__n, __a);
00174 try
00175 {
00176 if (__n)
00177 traits_type::assign(__r->_M_refdata(), __n, __c);
00178 }
00179 catch(...)
00180 {
00181 __r->_M_destroy(__a);
00182 __throw_exception_again;
00183 }
00184 __r->_M_length = __n;
00185 __r->_M_refdata()[__n] = _Rep::_S_terminal;
00186 return __r->_M_refdata();
00187 }
00188
00189 template<typename _CharT, typename _Traits, typename _Alloc>
00190 basic_string<_CharT, _Traits, _Alloc>::
00191 basic_string(const basic_string& __str)
00192 : _M_dataplus(__str._M_rep()->_M_grab(_Alloc(), __str.get_allocator()),
00193 __str.get_allocator())
00194 { }
00195
00196 template<typename _CharT, typename _Traits, typename _Alloc>
00197 basic_string<_CharT, _Traits, _Alloc>::
00198 basic_string(const _Alloc& __a)
00199 : _M_dataplus(_S_construct(size_type(), _CharT(), __a), __a)
00200 { }
00201
00202 template<typename _CharT, typename _Traits, typename _Alloc>
00203 basic_string<_CharT, _Traits, _Alloc>::
00204 basic_string(const basic_string& __str, size_type __pos, size_type __n)
00205 : _M_dataplus(_S_construct(__str._M_check(__pos),
00206 __str._M_fold(__pos, __n), _Alloc()), _Alloc())
00207 { }
00208
00209 template<typename _CharT, typename _Traits, typename _Alloc>
00210 basic_string<_CharT, _Traits, _Alloc>::
00211 basic_string(const basic_string& __str, size_type __pos,
00212 size_type __n, const _Alloc& __a)
00213 : _M_dataplus(_S_construct(__str._M_check(__pos),
00214 __str._M_fold(__pos, __n), __a), __a)
00215 { }
00216
00217 template<typename _CharT, typename _Traits, typename _Alloc>
00218 basic_string<_CharT, _Traits, _Alloc>::
00219 basic_string(const _CharT* __s, size_type __n, const _Alloc& __a)
00220 : _M_dataplus(_S_construct(__s, __s + __n, __a), __a)
00221 { }
00222
00223 template<typename _CharT, typename _Traits, typename _Alloc>
00224 basic_string<_CharT, _Traits, _Alloc>::
00225 basic_string(const _CharT* __s, const _Alloc& __a)
00226 : _M_dataplus(_S_construct(__s, __s ? __s + traits_type::length(__s) :
00227 __s + npos, __a), __a)
00228 { }
00229
00230 template<typename _CharT, typename _Traits, typename _Alloc>
00231 basic_string<_CharT, _Traits, _Alloc>::
00232 basic_string(size_type __n, _CharT __c, const _Alloc& __a)
00233 : _M_dataplus(_S_construct(__n, __c, __a), __a)
00234 { }
00235
00236 template<typename _CharT, typename _Traits, typename _Alloc>
00237 template<typename _InputIter>
00238 basic_string<_CharT, _Traits, _Alloc>::
00239 basic_string(_InputIter __beg, _InputIter __end, const _Alloc& __a)
00240 : _M_dataplus(_S_construct(__beg, __end, __a), __a)
00241 { }
00242
00243 template<typename _CharT, typename _Traits, typename _Alloc>
00244 basic_string<_CharT, _Traits, _Alloc>&
00245 basic_string<_CharT, _Traits, _Alloc>::assign(const basic_string& __str)
00246 {
00247 if (_M_rep() != __str._M_rep())
00248 {
00249
00250 allocator_type __a = this->get_allocator();
00251 _CharT* __tmp = __str._M_rep()->_M_grab(__a, __str.get_allocator());
00252 _M_rep()->_M_dispose(__a);
00253 _M_data(__tmp);
00254 }
00255 return *this;
00256 }
00257
00258 template<typename _CharT, typename _Traits, typename _Alloc>
00259 basic_string<_CharT, _Traits, _Alloc>&
00260 basic_string<_CharT, _Traits, _Alloc>::
00261 assign(const basic_string& __str, size_type __pos, size_type __n)
00262 {
00263 const size_type __strsize = __str.size();
00264 if (__pos > __strsize)
00265 __throw_out_of_range("basic_string::assign");
00266 const bool __testn = __n < __strsize - __pos;
00267 const size_type __newsize = __testn ? __n : __strsize - __pos;
00268 return this->assign(__str._M_data() + __pos, __newsize);
00269 }
00270
00271 template<typename _CharT, typename _Traits, typename _Alloc>
00272 basic_string<_CharT, _Traits, _Alloc>&
00273 basic_string<_CharT, _Traits, _Alloc>::
00274 assign(const _CharT* __s, size_type __n)
00275 {
00276 if (__n > this->max_size())
00277 __throw_length_error("basic_string::assign");
00278 if (_M_rep()->_M_is_shared() || less<const _CharT*>()(__s, _M_data())
00279 || less<const _CharT*>()(_M_data() + this->size(), __s))
00280 return _M_replace_safe(_M_ibegin(), _M_iend(), __s, __s + __n);
00281 else
00282 {
00283
00284 const size_type __pos = __s - _M_data();
00285 if (__pos >= __n)
00286 traits_type::copy(_M_data(), __s, __n);
00287 else if (__pos)
00288 traits_type::move(_M_data(), __s, __n);
00289 _M_rep()->_M_length = __n;
00290 _M_data()[__n] = _Rep::_S_terminal;
00291 return *this;
00292 }
00293 }
00294
00295 template<typename _CharT, typename _Traits, typename _Alloc>
00296 basic_string<_CharT, _Traits, _Alloc>&
00297 basic_string<_CharT, _Traits, _Alloc>::
00298 insert(size_type __pos1, const basic_string& __str,
00299 size_type __pos2, size_type __n)
00300 {
00301 const size_type __strsize = __str.size();
00302 if (__pos2 > __strsize)
00303 __throw_out_of_range("basic_string::insert");
00304 const bool __testn = __n < __strsize - __pos2;
00305 const size_type __newsize = __testn ? __n : __strsize - __pos2;
00306 return this->insert(__pos1, __str._M_data() + __pos2, __newsize);
00307 }
00308
00309 template<typename _CharT, typename _Traits, typename _Alloc>
00310 basic_string<_CharT, _Traits, _Alloc>&
00311 basic_string<_CharT, _Traits, _Alloc>::
00312 insert(size_type __pos, const _CharT* __s, size_type __n)
00313 {
00314 const size_type __size = this->size();
00315 if (__pos > __size)
00316 __throw_out_of_range("basic_string::insert");
00317 if (__size > this->max_size() - __n)
00318 __throw_length_error("basic_string::insert");
00319 if (_M_rep()->_M_is_shared() || less<const _CharT*>()(__s, _M_data())
00320 || less<const _CharT*>()(_M_data() + __size, __s))
00321 return _M_replace_safe(_M_ibegin() + __pos, _M_ibegin() + __pos,
00322 __s, __s + __n);
00323 else
00324 {
00325
00326
00327
00328 const size_type __off = __s - _M_data();
00329 _M_mutate(__pos, 0, __n);
00330 __s = _M_data() + __off;
00331 _CharT* __p = _M_data() + __pos;
00332 if (__s + __n <= __p)
00333 traits_type::copy(__p, __s, __n);
00334 else if (__s >= __p)
00335 traits_type::copy(__p, __s + __n, __n);
00336 else
00337 {
00338 traits_type::copy(__p, __s, __p - __s);
00339 traits_type::copy(__p + (__p-__s), __p + __n, __n - (__p-__s));
00340 }
00341 return *this;
00342 }
00343 }
00344
00345 template<typename _CharT, typename _Traits, typename _Alloc>
00346 basic_string<_CharT, _Traits, _Alloc>&
00347 basic_string<_CharT, _Traits, _Alloc>::
00348 replace(size_type __pos, size_type __n1, const _CharT* __s,
00349 size_type __n2)
00350 {
00351 const size_type __size = this->size();
00352 if (__pos > __size)
00353 __throw_out_of_range("basic_string::replace");
00354 const bool __testn1 = __n1 < __size - __pos;
00355 const size_type __foldn1 = __testn1 ? __n1 : __size - __pos;
00356 if (__size - __foldn1 > this->max_size() - __n2)
00357 __throw_length_error("basic_string::replace");
00358 if (_M_rep()->_M_is_shared() || less<const _CharT*>()(__s, _M_data())
00359 || less<const _CharT*>()(_M_data() + __size, __s))
00360 return _M_replace_safe(_M_ibegin() + __pos,
00361 _M_ibegin() + __pos + __foldn1, __s, __s + __n2);
00362
00363 else
00364 return _M_replace(_M_ibegin() + __pos, _M_ibegin() + __pos + __foldn1,
00365 __s, __s + __n2,
00366 typename iterator_traits<const _CharT*>::iterator_category());
00367 }
00368
00369 template<typename _CharT, typename _Traits, typename _Alloc>
00370 void
00371 basic_string<_CharT, _Traits, _Alloc>::_Rep::
00372 _M_destroy(const _Alloc& __a) throw ()
00373 {
00374 size_type __size = sizeof(_Rep) + (_M_capacity + 1) * sizeof(_CharT);
00375 _Raw_bytes_alloc(__a).deallocate(reinterpret_cast<char*>(this), __size);
00376 }
00377
00378 template<typename _CharT, typename _Traits, typename _Alloc>
00379 void
00380 basic_string<_CharT, _Traits, _Alloc>::_M_leak_hard()
00381 {
00382 if (_M_rep()->_M_is_shared())
00383 _M_mutate(0, 0, 0);
00384 _M_rep()->_M_set_leaked();
00385 }
00386
00387
00388
00389
00390
00391
00392
00393 template<typename _CharT, typename _Traits, typename _Alloc>
00394 void
00395 basic_string<_CharT, _Traits, _Alloc>::
00396 _M_mutate(size_type __pos, size_type __len1, size_type __len2)
00397 {
00398 size_type __old_size = this->size();
00399 const size_type __new_size = __old_size + __len2 - __len1;
00400 const _CharT* __src = _M_data() + __pos + __len1;
00401 const size_type __how_much = __old_size - __pos - __len1;
00402
00403 if (_M_rep()->_M_is_shared() || __new_size > capacity())
00404 {
00405
00406 allocator_type __a = get_allocator();
00407
00408
00409 const size_type __pagesize = 4096;
00410 const size_type __malloc_header_size = 4 * sizeof (void*);
00411
00412 const size_type __page_capacity = (__pagesize - __malloc_header_size
00413 - sizeof(_Rep) - sizeof(_CharT))
00414 / sizeof(_CharT);
00415 _Rep* __r;
00416 if (__new_size > capacity() && __new_size > __page_capacity)
00417
00418 __r = _Rep::_S_create(__new_size > 2*capacity() ?
00419 __new_size : 2*capacity(), __a);
00420 else
00421 __r = _Rep::_S_create(__new_size, __a);
00422 try
00423 {
00424 if (__pos)
00425 traits_type::copy(__r->_M_refdata(), _M_data(), __pos);
00426 if (__how_much)
00427 traits_type::copy(__r->_M_refdata() + __pos + __len2,
00428 __src, __how_much);
00429 }
00430 catch(...)
00431 {
00432 __r->_M_dispose(get_allocator());
00433 __throw_exception_again;
00434 }
00435 _M_rep()->_M_dispose(__a);
00436 _M_data(__r->_M_refdata());
00437 }
00438 else if (__how_much && __len1 != __len2)
00439 {
00440
00441 traits_type::move(_M_data() + __pos + __len2, __src, __how_much);
00442 }
00443 _M_rep()->_M_set_sharable();
00444 _M_rep()->_M_length = __new_size;
00445 _M_data()[__new_size] = _Rep::_S_terminal;
00446
00447 }
00448
00449 template<typename _CharT, typename _Traits, typename _Alloc>
00450 void
00451 basic_string<_CharT, _Traits, _Alloc>::reserve(size_type __res)
00452 {
00453 if (__res > this->capacity() || _M_rep()->_M_is_shared())
00454 {
00455 if (__res > this->max_size())
00456 __throw_length_error("basic_string::reserve");
00457
00458 if (__res < this->size())
00459 __res = this->size();
00460 allocator_type __a = get_allocator();
00461 _CharT* __tmp = _M_rep()->_M_clone(__a, __res - this->size());
00462 _M_rep()->_M_dispose(__a);
00463 _M_data(__tmp);
00464 }
00465 }
00466
00467 template<typename _CharT, typename _Traits, typename _Alloc>
00468 void basic_string<_CharT, _Traits, _Alloc>::swap(basic_string& __s)
00469 {
00470 if (_M_rep()->_M_is_leaked())
00471 _M_rep()->_M_set_sharable();
00472 if (__s._M_rep()->_M_is_leaked())
00473 __s._M_rep()->_M_set_sharable();
00474 if (this->get_allocator() == __s.get_allocator())
00475 {
00476 _CharT* __tmp = _M_data();
00477 _M_data(__s._M_data());
00478 __s._M_data(__tmp);
00479 }
00480
00481 else
00482 {
00483 basic_string __tmp1(_M_ibegin(), _M_iend(), __s.get_allocator());
00484 basic_string __tmp2(__s._M_ibegin(), __s._M_iend(),
00485 this->get_allocator());
00486 *this = __tmp2;
00487 __s = __tmp1;
00488 }
00489 }
00490
00491 template<typename _CharT, typename _Traits, typename _Alloc>
00492 typename basic_string<_CharT, _Traits, _Alloc>::_Rep*
00493 basic_string<_CharT, _Traits, _Alloc>::_Rep::
00494 _S_create(size_t __capacity, const _Alloc& __alloc)
00495 {
00496 typedef basic_string<_CharT, _Traits, _Alloc> __string_type;
00497 #ifdef _GLIBCPP_RESOLVE_LIB_DEFECTS
00498
00499 if (__capacity > _S_max_size)
00500 #else
00501 if (__capacity == npos)
00502 #endif
00503 __throw_length_error("basic_string::_S_create");
00504
00505
00506
00507
00508 size_t __size = (__capacity + 1) * sizeof(_CharT) + sizeof(_Rep);
00509
00510
00511
00512
00513
00514
00515
00516
00517
00518
00519
00520
00521
00522
00523
00524
00525
00526
00527
00528
00529
00530
00531
00532 const size_t __pagesize = 4096;
00533 const size_t __subpagesize = 128;
00534 const size_t __malloc_header_size = 4 * sizeof (void*);
00535 if ((__size + __malloc_header_size) > __pagesize)
00536 {
00537 size_t __extra =
00538 (__pagesize - ((__size + __malloc_header_size) % __pagesize))
00539 % __pagesize;
00540 __capacity += __extra / sizeof(_CharT);
00541 __size = (__capacity + 1) * sizeof(_CharT) + sizeof(_Rep);
00542 }
00543 else if (__size > __subpagesize)
00544 {
00545 size_t __extra =
00546 (__subpagesize - ((__size + __malloc_header_size) % __subpagesize))
00547 % __subpagesize;
00548 __capacity += __extra / sizeof(_CharT);
00549 __size = (__capacity + 1) * sizeof(_CharT) + sizeof(_Rep);
00550 }
00551
00552
00553
00554 void* __place = _Raw_bytes_alloc(__alloc).allocate(__size);
00555 _Rep *__p = new (__place) _Rep;
00556 __p->_M_capacity = __capacity;
00557 __p->_M_set_sharable();
00558 __p->_M_length = 0;
00559 return __p;
00560 }
00561
00562 template<typename _CharT, typename _Traits, typename _Alloc>
00563 _CharT*
00564 basic_string<_CharT, _Traits, _Alloc>::_Rep::
00565 _M_clone(const _Alloc& __alloc, size_type __res)
00566 {
00567
00568 const size_type __requested_cap = _M_length + __res;
00569
00570 const size_type __pagesize = 4096;
00571 const size_type __malloc_header_size = 4 * sizeof (void*);
00572
00573 const size_type __page_capacity =
00574 (__pagesize - __malloc_header_size - sizeof(_Rep) - sizeof(_CharT))
00575 / sizeof(_CharT);
00576 _Rep* __r;
00577 if (__requested_cap > _M_capacity && __requested_cap > __page_capacity)
00578
00579 __r = _Rep::_S_create(__requested_cap > 2*_M_capacity ?
00580 __requested_cap : 2*_M_capacity, __alloc);
00581 else
00582 __r = _Rep::_S_create(__requested_cap, __alloc);
00583
00584 if (_M_length)
00585 {
00586 try
00587 { traits_type::copy(__r->_M_refdata(), _M_refdata(), _M_length); }
00588 catch(...)
00589 {
00590 __r->_M_destroy(__alloc);
00591 __throw_exception_again;
00592 }
00593 }
00594 __r->_M_length = _M_length;
00595 return __r->_M_refdata();
00596 }
00597
00598 template<typename _CharT, typename _Traits, typename _Alloc>
00599 void
00600 basic_string<_CharT, _Traits, _Alloc>::resize(size_type __n, _CharT __c)
00601 {
00602 if (__n > max_size())
00603 __throw_length_error("basic_string::resize");
00604 size_type __size = this->size();
00605 if (__size < __n)
00606 this->append(__n - __size, __c);
00607 else if (__n < __size)
00608 this->erase(__n);
00609
00610 }
00611
00612
00613
00614
00615 template<typename _CharT, typename _Traits, typename _Alloc>
00616 template<typename _InputIter>
00617 basic_string<_CharT, _Traits, _Alloc>&
00618 basic_string<_CharT, _Traits, _Alloc>::
00619 _M_replace(iterator __i1, iterator __i2, _InputIter __k1,
00620 _InputIter __k2, input_iterator_tag)
00621 {
00622
00623 basic_string __s(__k1, __k2);
00624 return _M_replace_safe(__i1, __i2, __s._M_ibegin(), __s._M_iend());
00625 }
00626
00627
00628
00629
00630 template<typename _CharT, typename _Traits, typename _Alloc>
00631 template<typename _ForwardIter>
00632 basic_string<_CharT, _Traits, _Alloc>&
00633 basic_string<_CharT, _Traits, _Alloc>::
00634 _M_replace_safe(iterator __i1, iterator __i2, _ForwardIter __k1,
00635 _ForwardIter __k2)
00636 {
00637 size_type __dnew = static_cast<size_type>(std::distance(__k1, __k2));
00638 size_type __dold = __i2 - __i1;
00639 size_type __dmax = this->max_size();
00640
00641 if (__dmax <= __dnew)
00642 __throw_length_error("basic_string::_M_replace");
00643 size_type __off = __i1 - _M_ibegin();
00644 _M_mutate(__off, __dold, __dnew);
00645
00646
00647 if (__dnew)
00648 _S_copy_chars(_M_data() + __off, __k1, __k2);
00649
00650 return *this;
00651 }
00652
00653 template<typename _CharT, typename _Traits, typename _Alloc>
00654 basic_string<_CharT, _Traits, _Alloc>&
00655 basic_string<_CharT, _Traits, _Alloc>::
00656 replace(size_type __pos1, size_type __n1, const basic_string& __str,
00657 size_type __pos2, size_type __n2)
00658 {
00659 const size_type __strsize = __str.size();
00660 if (__pos2 > __strsize)
00661 __throw_out_of_range("basic_string::replace");
00662 const bool __testn2 = __n2 < __strsize - __pos2;
00663 const size_type __foldn2 = __testn2 ? __n2 : __strsize - __pos2;
00664 return this->replace(__pos1, __n1,
00665 __str._M_data() + __pos2, __foldn2);
00666 }
00667
00668 template<typename _CharT, typename _Traits, typename _Alloc>
00669 basic_string<_CharT, _Traits, _Alloc>&
00670 basic_string<_CharT, _Traits, _Alloc>::
00671 append(const basic_string& __str)
00672 {
00673
00674
00675
00676 size_type __size = __str.size();
00677 size_type __len = __size + this->size();
00678 if (__len > this->capacity())
00679 this->reserve(__len);
00680 return _M_replace_safe(_M_iend(), _M_iend(), __str._M_ibegin(),
00681 __str._M_iend());
00682 }
00683
00684 template<typename _CharT, typename _Traits, typename _Alloc>
00685 basic_string<_CharT, _Traits, _Alloc>&
00686 basic_string<_CharT, _Traits, _Alloc>::
00687 append(const basic_string& __str, size_type __pos, size_type __n)
00688 {
00689
00690
00691
00692 size_type __len = std::min(size_type(__str.size() - __pos),
00693 __n) + this->size();
00694 if (__len > this->capacity())
00695 this->reserve(__len);
00696 return _M_replace_safe(_M_iend(), _M_iend(), __str._M_check(__pos),
00697 __str._M_fold(__pos, __n));
00698 }
00699
00700 template<typename _CharT, typename _Traits, typename _Alloc>
00701 basic_string<_CharT, _Traits, _Alloc>&
00702 basic_string<_CharT, _Traits, _Alloc>::
00703 append(const _CharT* __s, size_type __n)
00704 {
00705 size_type __len = __n + this->size();
00706 if (__len > this->capacity())
00707 this->reserve(__len);
00708 return _M_replace_safe(_M_iend(), _M_iend(), __s, __s + __n);
00709 }
00710
00711 template<typename _CharT, typename _Traits, typename _Alloc>
00712 basic_string<_CharT, _Traits, _Alloc>&
00713 basic_string<_CharT, _Traits, _Alloc>::
00714 append(size_type __n, _CharT __c)
00715 {
00716 size_type __len = __n + this->size();
00717 if (__len > this->capacity())
00718 this->reserve(__len);
00719 return this->replace(_M_iend(), _M_iend(), __n, __c);
00720 }
00721
00722 template<typename _CharT, typename _Traits, typename _Alloc>
00723 basic_string<_CharT, _Traits, _Alloc>
00724 operator+(const _CharT* __lhs,
00725 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
00726 {
00727 typedef basic_string<_CharT, _Traits, _Alloc> __string_type;
00728 typedef typename __string_type::size_type __size_type;
00729 __size_type __len = _Traits::length(__lhs);
00730 __string_type __str;
00731 __str.reserve(__len + __rhs.size());
00732 __str.append(__lhs, __lhs + __len);
00733 __str.append(__rhs);
00734 return __str;
00735 }
00736
00737 template<typename _CharT, typename _Traits, typename _Alloc>
00738 basic_string<_CharT, _Traits, _Alloc>
00739 operator+(_CharT __lhs, const basic_string<_CharT, _Traits, _Alloc>& __rhs)
00740 {
00741 typedef basic_string<_CharT, _Traits, _Alloc> __string_type;
00742 typedef typename __string_type::size_type __size_type;
00743 __string_type __str;
00744 __size_type __len = __rhs.size();
00745 __str.reserve(__len + 1);
00746 __str.append(__size_type(1), __lhs);
00747 __str.append(__rhs);
00748 return __str;
00749 }
00750
00751 template<typename _CharT, typename _Traits, typename _Alloc>
00752 basic_string<_CharT, _Traits, _Alloc>&
00753 basic_string<_CharT, _Traits, _Alloc>::
00754 replace(iterator __i1, iterator __i2, size_type __n2, _CharT __c)
00755 {
00756 size_type __n1 = __i2 - __i1;
00757 size_type __off1 = __i1 - _M_ibegin();
00758 if (max_size() - (this->size() - __n1) <= __n2)
00759 __throw_length_error("basic_string::replace");
00760 _M_mutate (__off1, __n1, __n2);
00761
00762 if (__n2)
00763 traits_type::assign(_M_data() + __off1, __n2, __c);
00764 return *this;
00765 }
00766
00767 template<typename _CharT, typename _Traits, typename _Alloc>
00768 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00769 basic_string<_CharT, _Traits, _Alloc>::
00770 copy(_CharT* __s, size_type __n, size_type __pos) const
00771 {
00772 if (__pos > this->size())
00773 __throw_out_of_range("basic_string::copy");
00774
00775 if (__n > this->size() - __pos)
00776 __n = this->size() - __pos;
00777
00778 traits_type::copy(__s, _M_data() + __pos, __n);
00779
00780 return __n;
00781 }
00782
00783 template<typename _CharT, typename _Traits, typename _Alloc>
00784 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00785 basic_string<_CharT, _Traits, _Alloc>::
00786 find(const _CharT* __s, size_type __pos, size_type __n) const
00787 {
00788 size_type __size = this->size();
00789 size_t __xpos = __pos;
00790 const _CharT* __data = _M_data();
00791 for (; __xpos + __n <= __size; ++__xpos)
00792 if (traits_type::compare(__data + __xpos, __s, __n) == 0)
00793 return __xpos;
00794 return npos;
00795 }
00796
00797 template<typename _CharT, typename _Traits, typename _Alloc>
00798 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00799 basic_string<_CharT, _Traits, _Alloc>::
00800 find(_CharT __c, size_type __pos) const
00801 {
00802 size_type __size = this->size();
00803 size_type __ret = npos;
00804 if (__pos < __size)
00805 {
00806 const _CharT* __data = _M_data();
00807 size_type __n = __size - __pos;
00808 const _CharT* __p = traits_type::find(__data + __pos, __n, __c);
00809 if (__p)
00810 __ret = __p - __data;
00811 }
00812 return __ret;
00813 }
00814
00815
00816 template<typename _CharT, typename _Traits, typename _Alloc>
00817 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00818 basic_string<_CharT, _Traits, _Alloc>::
00819 rfind(const _CharT* __s, size_type __pos, size_type __n) const
00820 {
00821 size_type __size = this->size();
00822 if (__n <= __size)
00823 {
00824 __pos = std::min(size_type(__size - __n), __pos);
00825 const _CharT* __data = _M_data();
00826 do
00827 {
00828 if (traits_type::compare(__data + __pos, __s, __n) == 0)
00829 return __pos;
00830 }
00831 while (__pos-- > 0);
00832 }
00833 return npos;
00834 }
00835
00836 template<typename _CharT, typename _Traits, typename _Alloc>
00837 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00838 basic_string<_CharT, _Traits, _Alloc>::
00839 rfind(_CharT __c, size_type __pos) const
00840 {
00841 size_type __size = this->size();
00842 if (__size)
00843 {
00844 size_t __xpos = __size - 1;
00845 if (__xpos > __pos)
00846 __xpos = __pos;
00847
00848 for (++__xpos; __xpos-- > 0; )
00849 if (traits_type::eq(_M_data()[__xpos], __c))
00850 return __xpos;
00851 }
00852 return npos;
00853 }
00854
00855 template<typename _CharT, typename _Traits, typename _Alloc>
00856 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00857 basic_string<_CharT, _Traits, _Alloc>::
00858 find_first_of(const _CharT* __s, size_type __pos, size_type __n) const
00859 {
00860 for (; __n && __pos < this->size(); ++__pos)
00861 {
00862 const _CharT* __p = traits_type::find(__s, __n, _M_data()[__pos]);
00863 if (__p)
00864 return __pos;
00865 }
00866 return npos;
00867 }
00868
00869 template<typename _CharT, typename _Traits, typename _Alloc>
00870 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00871 basic_string<_CharT, _Traits, _Alloc>::
00872 find_last_of(const _CharT* __s, size_type __pos, size_type __n) const
00873 {
00874 size_type __size = this->size();
00875 if (__size && __n)
00876 {
00877 if (--__size > __pos)
00878 __size = __pos;
00879 do
00880 {
00881 if (traits_type::find(__s, __n, _M_data()[__size]))
00882 return __size;
00883 }
00884 while (__size-- != 0);
00885 }
00886 return npos;
00887 }
00888
00889 template<typename _CharT, typename _Traits, typename _Alloc>
00890 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00891 basic_string<_CharT, _Traits, _Alloc>::
00892 find_first_not_of(const _CharT* __s, size_type __pos, size_type __n) const
00893 {
00894 size_t __xpos = __pos;
00895 for (; __xpos < this->size(); ++__xpos)
00896 if (!traits_type::find(__s, __n, _M_data()[__xpos]))
00897 return __xpos;
00898 return npos;
00899 }
00900
00901 template<typename _CharT, typename _Traits, typename _Alloc>
00902 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00903 basic_string<_CharT, _Traits, _Alloc>::
00904 find_first_not_of(_CharT __c, size_type __pos) const
00905 {
00906 size_t __xpos = __pos;
00907 for (; __xpos < this->size(); ++__xpos)
00908 if (!traits_type::eq(_M_data()[__xpos], __c))
00909 return __xpos;
00910 return npos;
00911 }
00912
00913 template<typename _CharT, typename _Traits, typename _Alloc>
00914 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00915 basic_string<_CharT, _Traits, _Alloc>::
00916 find_last_not_of(const _CharT* __s, size_type __pos, size_type __n) const
00917 {
00918 size_type __size = this->size();
00919 if (__size)
00920 {
00921 if (--__size > __pos)
00922 __size = __pos;
00923 do
00924 {
00925 if (!traits_type::find(__s, __n, _M_data()[__size]))
00926 return __size;
00927 }
00928 while (__size--);
00929 }
00930 return npos;
00931 }
00932
00933 template<typename _CharT, typename _Traits, typename _Alloc>
00934 typename basic_string<_CharT, _Traits, _Alloc>::size_type
00935 basic_string<_CharT, _Traits, _Alloc>::
00936 find_last_not_of(_CharT __c, size_type __pos) const
00937 {
00938 size_type __size = this->size();
00939 if (__size)
00940 {
00941 if (--__size > __pos)
00942 __size = __pos;
00943 do
00944 {
00945 if (!traits_type::eq(_M_data()[__size], __c))
00946 return __size;
00947 }
00948 while (__size--);
00949 }
00950 return npos;
00951 }
00952
00953 template<typename _CharT, typename _Traits, typename _Alloc>
00954 int
00955 basic_string<_CharT, _Traits, _Alloc>::
00956 compare(size_type __pos, size_type __n, const basic_string& __str) const
00957 {
00958 size_type __size = this->size();
00959 size_type __osize = __str.size();
00960 if (__pos > __size)
00961 __throw_out_of_range("basic_string::compare");
00962
00963 size_type __rsize= std::min(size_type(__size - __pos), __n);
00964 size_type __len = std::min(__rsize, __osize);
00965 int __r = traits_type::compare(_M_data() + __pos, __str.data(), __len);
00966 if (!__r)
00967 __r = __rsize - __osize;
00968 return __r;
00969 }
00970
00971 template<typename _CharT, typename _Traits, typename _Alloc>
00972 int
00973 basic_string<_CharT, _Traits, _Alloc>::
00974 compare(size_type __pos1, size_type __n1, const basic_string& __str,
00975 size_type __pos2, size_type __n2) const
00976 {
00977 size_type __size = this->size();
00978 size_type __osize = __str.size();
00979 if (__pos1 > __size || __pos2 > __osize)
00980 __throw_out_of_range("basic_string::compare");
00981
00982 size_type __rsize = std::min(size_type(__size - __pos1), __n1);
00983 size_type __rosize = std::min(size_type(__osize - __pos2), __n2);
00984 size_type __len = std::min(__rsize, __rosize);
00985 int __r = traits_type::compare(_M_data() + __pos1,
00986 __str.data() + __pos2, __len);
00987 if (!__r)
00988 __r = __rsize - __rosize;
00989 return __r;
00990 }
00991
00992
00993 template<typename _CharT, typename _Traits, typename _Alloc>
00994 int
00995 basic_string<_CharT, _Traits, _Alloc>::
00996 compare(const _CharT* __s) const
00997 {
00998 size_type __size = this->size();
00999 size_type __osize = traits_type::length(__s);
01000 size_type __len = std::min(__size, __osize);
01001 int __r = traits_type::compare(_M_data(), __s, __len);
01002 if (!__r)
01003 __r = __size - __osize;
01004 return __r;
01005 }
01006
01007
01008 template<typename _CharT, typename _Traits, typename _Alloc>
01009 int
01010 basic_string <_CharT, _Traits, _Alloc>::
01011 compare(size_type __pos, size_type __n1, const _CharT* __s) const
01012 {
01013 size_type __size = this->size();
01014 if (__pos > __size)
01015 __throw_out_of_range("basic_string::compare");
01016
01017 size_type __osize = traits_type::length(__s);
01018 size_type __rsize = std::min(size_type(__size - __pos), __n1);
01019 size_type __len = std::min(__rsize, __osize);
01020 int __r = traits_type::compare(_M_data() + __pos, __s, __len);
01021 if (!__r)
01022 __r = __rsize - __osize;
01023 return __r;
01024 }
01025
01026 template<typename _CharT, typename _Traits, typename _Alloc>
01027 int
01028 basic_string <_CharT, _Traits, _Alloc>::
01029 compare(size_type __pos, size_type __n1, const _CharT* __s,
01030 size_type __n2) const
01031 {
01032 size_type __size = this->size();
01033 if (__pos > __size)
01034 __throw_out_of_range("basic_string::compare");
01035
01036 size_type __osize = std::min(traits_type::length(__s), __n2);
01037 size_type __rsize = std::min(size_type(__size - __pos), __n1);
01038 size_type __len = std::min(__rsize, __osize);
01039 int __r = traits_type::compare(_M_data() + __pos, __s, __len);
01040 if (!__r)
01041 __r = __rsize - __osize;
01042 return __r;
01043 }
01044
01045 template <class _CharT, class _Traits, class _Alloc>
01046 void
01047 _S_string_copy(const basic_string<_CharT, _Traits, _Alloc>& __str,
01048 _CharT* __buf, typename _Alloc::size_type __bufsiz)
01049 {
01050 typedef typename _Alloc::size_type size_type;
01051 size_type __strsize = __str.size();
01052 size_type __bytes = std::min(__strsize, __bufsiz - 1);
01053 _Traits::copy(__buf, __str.data(), __bytes);
01054 __buf[__bytes] = _CharT();
01055 }
01056
01057
01058
01059
01060 #if _GLIBCPP_EXTERN_TEMPLATE
01061 extern template class basic_string<char>;
01062 extern template
01063 basic_istream<char>&
01064 operator>>(basic_istream<char>&, string&);
01065 extern template
01066 basic_ostream<char>&
01067 operator<<(basic_ostream<char>&, const string&);
01068 extern template
01069 basic_istream<char>&
01070 getline(basic_istream<char>&, string&, char);
01071 extern template
01072 basic_istream<char>&
01073 getline(basic_istream<char>&, string&);
01074
01075 #ifdef _GLIBCPP_USE_WCHAR_T
01076 extern template class basic_string<wchar_t>;
01077 extern template
01078 basic_istream<wchar_t>&
01079 operator>>(basic_istream<wchar_t>&, wstring&);
01080 extern template
01081 basic_ostream<wchar_t>&
01082 operator<<(basic_ostream<wchar_t>&, const wstring&);
01083 extern template
01084 basic_istream<wchar_t>&
01085 getline(basic_istream<wchar_t>&, wstring&, wchar_t);
01086 extern template
01087 basic_istream<wchar_t>&
01088 getline(basic_istream<wchar_t>&, wstring&);
01089 #endif
01090 #endif
01091 }
01092
01093 #endif