3483#ifdef BSLSTL_STRING_VIEW_AND_STD_STRING_VIEW_COEXIST
3485 operator std::basic_string_view<CHAR_TYPE, CHAR_TRAITS>()
const;
3489#ifdef BSLS_COMPILERFEATURES_SUPPORT_CTAD
3502 class = bsl::enable_if_t<bsl::is_convertible_v<ALLOC, ALLOCATOR>>
3515 class = bsl::enable_if_t<bsl::is_convertible_v<ALLOC *, DEFAULT_ALLOCATOR>>
3529 class = bsl::enable_if_t<
3530 bsl::is_convertible_v<ALLOC *, DEFAULT_ALLOCATOR>>,
3531 class = bsl::enable_if_t<!bsl::is_pointer_v<SZ>>
3547 class = bsl::enable_if_t<bsl::is_convertible_v<ALLOC *, DEFAULT_ALLOCATOR>>
3563 class = bsl::enable_if_t<bsl::is_convertible_v<ALLOC *, ALLOCATOR>>
3576 typename BloombergLP::bslstl::IteratorUtil::IterVal_t<INPUT_ITER>,
3578 class = bsl::enable_if_t<bsl::IsStdAllocator_v<ALLOCATOR>>
3580basic_string(INPUT_ITER, INPUT_ITER, ALLOCATOR = ALLOCATOR())
3590 typename BloombergLP::bslstl::IteratorUtil::IterVal_t<INPUT_ITER>,
3593 class = bsl::enable_if_t<bsl::is_convertible_v<ALLOC *, DEFAULT_ALLOCATOR>>
3608 class = bsl::enable_if_t<bsl::IsStdAllocator_v<ALLOCATOR>>
3611 ALLOCATOR = ALLOCATOR())
3624 class = bsl::enable_if_t<bsl::is_convertible_v<ALLOC *, DEFAULT_ALLOCATOR>>
3637 class = bsl::enable_if_t<bsl::is_convertible_v<ALLOC *, DEFAULT_ALLOCATOR>>
3645template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3649template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3652 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
3659template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3661 const CHAR_TYPE *
rhs);
3663#ifdef BSLS_COMPILERFEATURES_SUPPORT_THREE_WAY_COMPARISON
3665template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3666String_ComparisonCategoryType<CHAR_TRAITS>
3674template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3675String_ComparisonCategoryType<CHAR_TRAITS>
3677 const CHAR_TYPE *
rhs);
3678template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3679String_ComparisonCategoryType<CHAR_TRAITS>
3681 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
3690template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3692operator==(
const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC1>&
lhs,
3695template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3696bool operator==(
const CHAR_TYPE *
lhs,
3703template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3707template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3709operator!=(
const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC1>&
lhs,
3712template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3715 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
3718template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3719bool operator!=(
const CHAR_TYPE *
lhs,
3721template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3723 const CHAR_TYPE *
rhs);
3728template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3732template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3734operator<(
const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC1>&
lhs,
3737template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3740 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
3742template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3744bool operator<(
const CHAR_TYPE *
lhs,
3746template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3748 const CHAR_TYPE *
rhs);
3750template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3754template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3756operator>(
const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC1>&
lhs,
3759template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3762 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
3768template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3769bool operator>(
const CHAR_TYPE *
lhs,
3771template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3773 const CHAR_TYPE *
rhs);
3778template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3782template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3784operator<=(
const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC1>&
lhs,
3787template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3790 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
3793template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3794bool operator<=(
const CHAR_TYPE *
lhs,
3796template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3798 const CHAR_TYPE *
rhs);
3803template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3807template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3809operator>=(
const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC1>&
lhs,
3812template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3815 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
3818template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3819bool operator>=(
const CHAR_TYPE *
lhs,
3821template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC>
3823 const CHAR_TYPE *
rhs);
3833template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3837#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3838template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3842template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3846template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3851template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3855#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3856template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3858operator+(
const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC1>&
lhs,
3861template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3864 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs);
3865#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3866template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOC1,
class ALLOC2>
3869 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs);
3871template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3875#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3876template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3881template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3885#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3886template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3891template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3894 const CHAR_TYPE *
rhs);
3895#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3896template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3899 const CHAR_TYPE *
rhs);
3901template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3905#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3906template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3911template <
class CHAR_TYPE,
3914 class STRING_VIEW_LIKE_TYPE>
3918 const STRING_VIEW_LIKE_TYPE &
rhs);
3919#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3920template <
class CHAR_TYPE,
3923 class STRING_VIEW_LIKE_TYPE>
3927 const STRING_VIEW_LIKE_TYPE &
rhs);
3929template <
class CHAR_TYPE,
3932 class STRING_VIEW_LIKE_TYPE>
3937#ifdef BSLSTL_STRING_SUPPORT_RVALUE_ADDITION_OPERATORS
3938template <
class CHAR_TYPE,
3941 class STRING_VIEW_LIKE_TYPE>
3954template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3955std::basic_ostream<CHAR_TYPE, CHAR_TRAITS>&
3956operator<<(std::basic_ostream<CHAR_TYPE, CHAR_TRAITS>& os,
3968template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
3969std::basic_istream<CHAR_TYPE, CHAR_TRAITS>&
3973#if defined (BSLS_LIBRARYFEATURES_HAS_CPP11_BASELINE_LIBRARY) && \
3974 defined (BSLS_COMPILERFEATURES_SUPPORT_INLINE_NAMESPACE)
3975inline namespace literals {
3976inline namespace string_literals {
3994 string operator ""_s(
const char *characterString, std::size_t length);
3995wstring operator ""_s(
const wchar_t *characterString, std::size_t length);
3997#if !defined(BSLS_PLATFORM_OS_SOLARIS) || \
3998 (defined(BSLS_PLATFORM_CMP_GNU) && BSLS_PLATFORM_CMP_VERSION >= 80000)
4012 string operator ""_S(
const char *characterString, std::size_t length);
4013wstring operator ""_S(
const wchar_t *characterString, std::size_t length);
4037template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4052template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4053std::basic_istream<CHAR_TYPE, CHAR_TRAITS>&
4054getline(std::basic_istream<CHAR_TYPE, CHAR_TRAITS>& is,
4067template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4068std::basic_istream<CHAR_TYPE, CHAR_TRAITS>&
4069getline(std::basic_istream<CHAR_TYPE, CHAR_TRAITS>& is,
4072int stoi(
const string& str, std::size_t *pos = 0,
int base = 10);
4074long stol(
const string& str, std::size_t *pos = 0,
int base = 10);
4076unsigned long stoul(
const string& str, std::size_t *pos = 0,
int base = 10);
4077unsigned long stoul(
const wstring& str, std::size_t *pos = 0,
int base = 10);
4078long long stoll(
const string& str, std::size_t *pos = 0,
int base = 10);
4103 std::size_t *pos = 0,
4106 std::size_t *pos = 0,
4109float stof(
const string& str, std::size_t *pos =0);
4111double stod(
const string& str, std::size_t *pos =0);
4124long double stold(
const string& str, std::size_t *pos =0);
4223template <
class CHAR_TYPE,
4226 class OTHER_CHAR_TYPE>
4229 const OTHER_CHAR_TYPE& c);
4234template <
class CHAR_TYPE,
4237 class UNARY_PREDICATE>
4240 const UNARY_PREDICATE& pred);
4268template <
class HASHALG,
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4273template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4285template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4287 : ::BloombergLP::bslh::Hash<>
4292 std::size_t operator()(
4298 std::size_t operator()(
const CHAR_TYPE *input)
const;
4301#if defined(BSLS_PLATFORM_CMP_SUN) && BSLS_PLATFORM_CMP_VERSION < 0x5130
4309struct hash<
string> : ::BloombergLP::bslh::Hash<>
4314 std::size_t operator()(
const string& input)
const;
4319 std::size_t operator()(
const char *input)
const;
4323struct hash<
wstring> : ::BloombergLP::bslh::Hash<>
4328 std::size_t operator()(
const wstring& input)
const;
4333 std::size_t operator()(
const wchar_t *input)
const;
4353template <
class HASHALG,
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4357 const std::basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>& input);
4373template <
class CHAR_TYPE,
class SIZE_TYPE>
4376 SIZE_TYPE oldCapacity,
4390 SIZE_TYPE newCapacity = oldCapacity + (oldCapacity >> 1);
4392 if (newLength > newCapacity) {
4393 newCapacity = newLength;
4396 if (newCapacity < oldCapacity || newCapacity > maxSize) {
4397 newCapacity = maxSize;
4404template <
class CHAR_TYPE,
class SIZE_TYPE>
4409, d_capacity(this->SHORT_BUFFER_CAPACITY)
4413template <
class CHAR_TYPE,
class SIZE_TYPE>
4419, d_capacity(capacity <= static_cast<SIZE_TYPE>(this->SHORT_BUFFER_CAPACITY)
4420 ? static_cast<SIZE_TYPE>(this->SHORT_BUFFER_CAPACITY)
4426template <
class CHAR_TYPE,
class SIZE_TYPE>
4431 BloombergLP::bslalg::ScalarPrimitives::swap(d_length, other.
d_length);
4432 BloombergLP::bslalg::ScalarPrimitives::swap(d_capacity,
4434 BloombergLP::bslalg::ScalarPrimitives::swap(d_start_p,
4440 BloombergLP::bslalg::ScalarPrimitives::swap(*
this, other);
4445template <
class CHAR_TYPE,
class SIZE_TYPE>
4451 d_capacity = this->SHORT_BUFFER_CAPACITY;
4455template <
class CHAR_TYPE,
class SIZE_TYPE>
4459 return isShortString()
4460 ?
reinterpret_cast<CHAR_TYPE *
>((
void *)d_short.buffer())
4465template <
class CHAR_TYPE,
class SIZE_TYPE>
4470#ifdef BSLS_PLATFORM_PRAGMA_GCC_DIAGNOSTIC_GCC
4471#pragma GCC diagnostic push
4472#pragma GCC diagnostic ignored "-Wmaybe-uninitialized"
4474 return d_capacity == this->SHORT_BUFFER_CAPACITY;
4476#ifdef BSLS_PLATFORM_PRAGMA_GCC_DIAGNOSTIC_GCC
4477#pragma GCC diagnostic pop
4481template <
class CHAR_TYPE,
class SIZE_TYPE>
4485 return isShortString()
4486 ?
reinterpret_cast<const CHAR_TYPE *
>((
const void *)d_short.buffer())
4495template <
class FULL_STRING_TYPE>
4497 FULL_STRING_TYPE *stringPtr)
4498: d_string_p(stringPtr)
4499, d_originalLength(stringPtr->d_length)
4501 d_string_p->d_length = 0;
4504template <
class FULL_STRING_TYPE>
4508 d_string_p->d_length = d_originalLength;
4513template <
class FULL_STRING_TYPE>
4524template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4529template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4533 bool maxLengthExceeded,
4534 const char *message)
4538 BloombergLP::bslstl::StdExceptUtil::throwLengthError(message);
4542template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4545basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>::privateThrowOutOfRange(
4547 const char *message)
4551 BloombergLP::bslstl::StdExceptUtil::throwOutOfRange(message);
4556template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4559basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateAllocate(
4562 return AllocatorUtil::allocateObject<CHAR_TYPE>(this->allocatorRef(),
4566template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4568void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateDeallocate()
4570 if (!this->isShortString()) {
4571 AllocatorUtil::deallocateObject(this->allocatorRef(),
4572 this->d_start_p, this->d_capacity + 1);
4576template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4579basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateCopyFromOutOfPlaceBuffer(
4580 const basic_string& original)
4589 static_cast<Imp &
>(*this) = Imp(original.length(), original.length());
4591 if (!this->isShortString()) {
4592 this->d_start_p = privateAllocate(this->d_capacity);
4595 CHAR_TRAITS::copy(this->dataPtr(), original.data(), this->d_length + 1);
4598template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4599basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
4600basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateAppend(
4601 const CHAR_TYPE *characterString,
4603 const char *message)
4605 privateThrowLengthError(numChars > max_size() - length(), message);
4607 size_type newLength = this->d_length + numChars;
4608 size_type newStorage = this->d_capacity;
4609 CHAR_TYPE *newBuffer = privateReserveRaw(&newStorage,
4614 CHAR_TRAITS::copy(newBuffer + this->d_length,
4617 CHAR_TRAITS::assign(*(newBuffer + newLength), CHAR_TYPE());
4619 privateDeallocate();
4621 this->d_start_p = newBuffer;
4622 this->d_capacity = newStorage;
4625 CHAR_TRAITS::move(this->dataPtr() + length(),
4628 CHAR_TRAITS::assign(*(this->dataPtr() + newLength), CHAR_TYPE());
4631 this->d_length = newLength;
4635template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4636basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
4637basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateAppend(
4639 CHAR_TYPE character,
4640 const char *message)
4642 privateThrowLengthError(numChars > max_size() - length(), message);
4644 size_type newLength = this->d_length + numChars;
4645 privateReserveRaw(newLength);
4646 CHAR_TRAITS::assign(this->dataPtr() + this->d_length, numChars, character);
4647 this->d_length = newLength;
4648 CHAR_TRAITS::assign(*(this->dataPtr() + newLength), CHAR_TYPE());
4652template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4654basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
4655basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateAppend(
4658 const char *message,
4659 std::forward_iterator_tag)
4663 return privateAppend(const_iterator(first),
4664 const_iterator(last),
4666 std::forward_iterator_tag());
4669template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4671basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
4672basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateAppend(
4673 const_iterator first,
4674 const_iterator last,
4675 const char *message,
4676 std::forward_iterator_tag)
4679 return privateAppend(&*first, last - first, message);
4682template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4683template <
class INPUT_ITER,
class SENTINEL>
4685basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
4689 const char *message,
4690 std::input_iterator_tag tag)
4692 return privateAppend(first, last, npos, message, tag);
4695template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4696template <
class INPUT_ITER,
class SENTINEL>
4703 const char *message,
4704 std::input_iterator_tag )
4709 for (; first != last; ++first) {
4712 if (length() == 0 && capacity() <= temp.
capacity()) {
4713 quickSwapRetainAllocators(temp);
4718 CHAR_TRAITS::assign(*(temp.dataPtr()), CHAR_TYPE());
4721 return privateAppend(temp.
data(), temp.
length(), message);
4724template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4725template <
class INPUT_ITER,
class SENTINEL>
4731 const char *message,
4732 std::forward_iterator_tag tag)
4734 size_type numChars = privateNumCharsInRange(first, last);
4735 return privateAppend(first, last, numChars, message, tag);
4738template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4739template <
class INPUT_ITER,
class SENTINEL>
4746 const char *message,
4747 std::forward_iterator_tag )
4750 BloombergLP::bslstl::IteratorUtil::insertDistance(first, last)));
4752 privateThrowLengthError(numChars > max_size() - length(), message);
4754 size_type newLength = this->d_length + numChars;
4755 size_type newStorage = this->d_capacity;
4756 CHAR_TYPE *newBuffer = privateReserveRaw(&newStorage,
4761 for (
size_type pos = this->d_length; first != last; ++first, ++pos) {
4762 CHAR_TRAITS::assign(*(newBuffer + pos), *first);
4765 privateDeallocate();
4767 this->d_start_p = newBuffer;
4768 this->d_capacity = newStorage;
4771 for (
size_type pos = this->d_length; first != last; ++first, ++pos) {
4772 CHAR_TRAITS::assign(*(this->dataPtr() + pos), *first);
4776 CHAR_TRAITS::assign(*(this->dataPtr() + newLength), CHAR_TYPE());
4777 this->d_length = newLength;
4781template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4782template <
class INPUT_ITER>
4788 const char *message)
4790 return privateAppendDispatch(first,
4794 BloombergLP::bslmf::Nil());
4797template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4798template <
class INPUT_ITER,
class SENTINEL>
4805 const char *message)
4807 typename iterator_traits<INPUT_ITER>::iterator_category tag;
4808 return privateAppend(first, last, numChars, message, tag);
4811template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4812template <
class INPUT_ITER>
4818 const char *message,
4819 BloombergLP::bslmf::MatchArithmeticType ,
4820 BloombergLP::bslmf::Nil )
4822 return privateAppend((
size_type)first, (CHAR_TYPE)last, message);
4825template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4826template <
class INPUT_ITER>
4832 const char *message,
4833 BloombergLP::bslmf::MatchAnyType ,
4834 BloombergLP::bslmf::MatchAnyType )
4836 typename iterator_traits<INPUT_ITER>::iterator_category tag;
4837 return privateAppend(first, last, message, tag);
4840template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4841template <
class FIRST_TYPE,
class SECOND_TYPE>
4847 const char *message)
4851 privateAppend(first, second, message);
4858template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4859template <
class INPUT_ITER,
class SENTINEL>
4866 const char *message)
4870 privateAppendRange(first, last, numChars, message);
4877template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4879typename basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>::Imp&
4882 return *
static_cast<Imp *
>(
this);
4885template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4886void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateClear(
4887 bool deallocateBufferFlag)
4889 if (deallocateBufferFlag) {
4890 privateDeallocate();
4891 this->resetFields();
4897 CHAR_TRAITS::assign(*
begin(), CHAR_TYPE());
4900template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4902void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateInsertDispatch(
4903 const_iterator position,
4909 privateInsertDispatch(position,
4910 const_iterator(first),
4911 const_iterator(last));
4914template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4915void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateInsertDispatch(
4916 const_iterator position,
4917 const_iterator first,
4918 const_iterator last)
4922 size_type pos = position -
cbegin();
4923 privateThrowOutOfRange(
4925 "string<...>::insert<Iter>(pos,i,j): invalid position");
4927 size_type numChars = last - first;
4928 privateThrowLengthError(
4929 numChars > max_size() - length(),
4930 "string<...>::insert<Iter>(pos,i,j): string too long");
4932 privateInsertRaw(pos, &*first, numChars);
4935template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4936template <
class INPUT_ITER>
4938void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateInsertDispatch(
4939 const_iterator position,
4943 size_type pos = position -
cbegin();
4944 privateReplaceDispatch(pos,
4949 BloombergLP::bslmf::Nil());
4952template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4953template <
class INPUT_ITER,
class SENTINEL>
4955void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateInsertRange(
4956 const_iterator position,
4957 size_type inNumChars,
4961 size_type outPosition = position -
cbegin();
4962 privateReplaceRange(outPosition, size_type(0), inNumChars, first, last);
4965template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
4966basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
4967basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateInsertRaw(
4968 size_type outPosition,
4969 const CHAR_TYPE *characterString,
4976 size_type newLength = this->d_length + numChars;
4977 size_type newStorage = this->d_capacity;
4978 CHAR_TYPE *newBuffer = privateReserveRaw(&newStorage,
4986 const CHAR_TYPE *tail = this->dataPtr() + outPosition;
4987 size_type tailLen = this->d_length - outPosition;
4989 CHAR_TRAITS::copy(newBuffer + outPosition, characterString, numChars);
4990 CHAR_TRAITS::copy(newBuffer + outPosition + numChars, tail, tailLen);
4991 CHAR_TRAITS::assign(*(newBuffer + newLength), CHAR_TYPE());
4993 privateDeallocate();
4995 this->d_start_p = newBuffer;
4996 this->d_capacity = newStorage;
5006 const CHAR_TYPE *first = characterString;
5007 const CHAR_TYPE *last = characterString + numChars;
5008 CHAR_TYPE *tail = this->dataPtr() + outPosition;
5009 size_type tailLen = this->d_length - outPosition;
5010 const CHAR_TYPE *shifted = (tail < first && last <= tail + tailLen)
5014 CHAR_TRAITS::move(tail + numChars, tail, tailLen);
5015 CHAR_TRAITS::move(tail, shifted, numChars);
5016 CHAR_TRAITS::assign(*(this->dataPtr() + newLength), CHAR_TYPE());
5019 this->d_length = newLength;
5023template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5024void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateMoveConstruct(
5025 basic_string& original,
5029 privateThrowOutOfRange(position > original.length(),
5030 "string(string&&,pos,n): invalid position");
5032 size_type len = length() - position;
5033 if (numChars < len) {
5036 this->d_length = len;
5038 CHAR_TYPE *
data = this->dataPtr();
5040 if (original.isShortString()) {
5041 CHAR_TRAITS::move(data, data + position, len);
5043 else if (this->get_allocator() == original.get_allocator()) {
5045 original.resetFields();
5046 CHAR_TRAITS::move(data, data + position, len);
5048 else if (len <= this->SHORT_BUFFER_CAPACITY) {
5049 this->d_capacity = this->SHORT_BUFFER_CAPACITY;
5050 data = this->dataPtr();
5051 CHAR_TRAITS::copy(data, original.data() + position, len);
5055 this->d_start_p =
data = privateAllocate(len);
5056 this->d_capacity = len;
5057 CHAR_TRAITS::copy(data, original.data() + position, len);
5059 CHAR_TRAITS::assign(data[len], CHAR_TYPE());
5062template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5063basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
5064basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateReplaceRaw(
5065 size_type outPosition,
5066 size_type outNumChars,
5067 const CHAR_TYPE *characterString,
5076 const difference_type displacement =
5077 static_cast<difference_type
>(numChars - outNumChars);
5079 size_type newLength = this->d_length + displacement;
5080 size_type newStorage = this->d_capacity;
5081 CHAR_TYPE *newBuffer = privateReserveRaw(&newStorage,
5085 const CHAR_TYPE *tail = this->dataPtr() + outPosition + outNumChars;
5086 size_type tailLen = this->d_length - outPosition - outNumChars;
5092 CHAR_TRAITS::copy(newBuffer + outPosition, characterString, numChars);
5093 CHAR_TRAITS::copy(newBuffer + outPosition + numChars, tail, tailLen);
5094 CHAR_TRAITS::assign(*(newBuffer + newLength), CHAR_TYPE());
5096 privateDeallocate();
5098 this->d_start_p = newBuffer;
5099 this->d_capacity = newStorage;
5100 this->d_length = newLength;
5108 CHAR_TYPE *dest = this->dataPtr() + outPosition;
5109 const CHAR_TYPE *first = characterString;
5110 const CHAR_TYPE *last = characterString + numChars;
5112 if (tail < last && last <= tail + tailLen) {
5120 size_type prefix = tail - first, suffix = last - tail;
5121 if (outNumChars < numChars) {
5122 CHAR_TRAITS::move(dest + numChars, tail, tailLen);
5123 CHAR_TRAITS::move(dest, first, prefix);
5126 CHAR_TRAITS::move(dest, first, prefix);
5127 CHAR_TRAITS::move(dest + numChars, tail, tailLen);
5129 CHAR_TRAITS::move(dest + prefix,
5130 last - suffix + displacement,
5137 CHAR_TRAITS::move(dest + numChars, tail, tailLen);
5138 CHAR_TRAITS::copy(dest, first + displacement, numChars);
5144 if (outNumChars < numChars) {
5145 CHAR_TRAITS::move(dest + numChars, tail, tailLen);
5146 CHAR_TRAITS::move(dest, characterString, numChars);
5149 CHAR_TRAITS::move(dest, characterString, numChars);
5150 CHAR_TRAITS::move(dest + numChars, tail, tailLen);
5153 CHAR_TRAITS::assign(*(this->dataPtr() + newLength), CHAR_TYPE());
5154 this->d_length = newLength;
5158template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5159basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
5160basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateReplaceRaw(
5161 size_type outPosition,
5162 size_type outNumChars,
5164 CHAR_TYPE character)
5171 size_type newLength = this->d_length - outNumChars + numChars;
5172 size_type newStorage = this->d_capacity;
5173 CHAR_TYPE *newBuffer = privateReserveRaw(&newStorage,
5177 const CHAR_TYPE *tail = this->dataPtr() + outPosition + outNumChars;
5178 size_type tailLen = this->d_length - outPosition - outNumChars;
5181 CHAR_TYPE *dest = newBuffer + outPosition;
5183 CHAR_TRAITS::assign(dest, numChars, character);
5184 CHAR_TRAITS::copy(dest + numChars, tail, tailLen);
5185 CHAR_TRAITS::assign(*(newBuffer + newLength), CHAR_TYPE());
5187 privateDeallocate();
5189 this->d_start_p = newBuffer;
5190 this->d_capacity = newStorage;
5193 CHAR_TYPE *dest = this->dataPtr() + outPosition;
5195 CHAR_TRAITS::move(dest + numChars, tail, tailLen);
5196 CHAR_TRAITS::assign(dest, numChars, character);
5197 CHAR_TRAITS::assign(*(this->dataPtr() + newLength), CHAR_TYPE());
5200 this->d_length = newLength;
5204template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5205template <
class INPUT_ITER>
5207basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
5213 BloombergLP::bslmf::MatchArithmeticType ,
5214 BloombergLP::bslmf::Nil )
5216 return replace(position, numChars, (
size_type)first, (CHAR_TYPE)last);
5219template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5220template <
class INPUT_ITER>
5228 BloombergLP::bslmf::MatchAnyType ,
5229 BloombergLP::bslmf::MatchAnyType )
5231 typename iterator_traits<INPUT_ITER>::iterator_category tag;
5232 return privateReplace(position, numChars, first, last, tag);
5235template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5236template <
class INPUT_ITER>
5243 std::input_iterator_tag tag)
5245 return privateReplace(outPosition, outNumChars, npos, first, last, tag);
5248template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5249template <
class INPUT_ITER,
class SENTINEL>
5257 std::input_iterator_tag )
5261 privateThrowOutOfRange(
5262 length() < outPosition,
5263 "string<...>::replace<InputIter>(pos,n,i,j): invalid position");
5266 for (; first != last; ++first) {
5269 if (outPosition == 0 && length() <= outNumChars) {
5272 temp.privateReserveRaw(capacity());
5273 quickSwapRetainAllocators(temp);
5276 return privateReplaceRaw(outPosition,
5282template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5283template <
class INPUT_ITER>
5290 std::forward_iterator_tag tag)
5292 size_type inNumChars = privateNumCharsInRange(first, last);
5293 return privateReplace(outPosition, outNumChars,
5300template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5301template <
class INPUT_ITER,
class SENTINEL>
5309 std::forward_iterator_tag )
5312 BloombergLP::bslstl::IteratorUtil::insertDistance(first, last)));
5315 privateThrowOutOfRange(
5316 length() < outPosition,
5317 "string<...>::replace<Iter>(pos,n,i,j): invalid position");
5319 privateThrowLengthError(
5320 max_size() - (length() - outPosition) < inNumChars,
5321 "string<...>::replace<Iter>(pos,n,i,j): string too long");
5328 for (
size_type pos = 0; pos != inNumChars; ++first, ++pos) {
5332 return privateReplaceRaw(outPosition,
5338template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5343 const_iterator first,
5344 const_iterator last,
5345 std::forward_iterator_tag)
5349 privateThrowOutOfRange(
5350 length() < position,
5351 "string<...>::replace<Iter>(pos,n,i,j): invalid position");
5353 size_type numNewChars = bsl::distance(first, last);
5354 privateThrowLengthError(
5355 max_size() - (length() - position) < numNewChars,
5356 "string<...>::replace<Iter>(pos,n,i,j): string too long");
5358 return privateReplaceRaw(position, numChars, &*first, numNewChars);
5361template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5363basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
5364basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateReplace(
5369 std::forward_iterator_tag)
5373 return privateReplace(position,
5375 const_iterator(first),
5376 const_iterator(last),
5377 std::forward_iterator_tag());
5380template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5381template <
class INPUT_ITER,
class SENTINEL>
5383basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
5391 typename iterator_traits<INPUT_ITER>::iterator_category tag;
5392 return privateReplace(position,
5400template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5402 size_type newCapacity)
5406 if (this->d_capacity < newCapacity) {
5407 size_type newStorage = this->computeNewCapacity(newCapacity,
5410 CHAR_TYPE *newBuffer = privateAllocate(newStorage);
5412 CHAR_TRAITS::copy(newBuffer, this->dataPtr(), this->d_length + 1);
5414 privateDeallocate();
5416 this->d_start_p = newBuffer;
5417 this->d_capacity = newStorage;
5421template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5423basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateReserveRaw(
5425 size_type newCapacity,
5432 if (*storage >= newCapacity) {
5436 *storage = this->computeNewCapacity(newCapacity,
5440 CHAR_TYPE *newBuffer = privateAllocate(*storage);
5442 CHAR_TRAITS::copy(newBuffer, this->dataPtr(), numChars);
5446template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5447basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
5448basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateResizeRaw(
5449 size_type newLength,
5450 CHAR_TYPE character)
5454 privateReserveRaw(newLength);
5456 if (newLength > this->d_length) {
5457 CHAR_TRAITS::assign(this->dataPtr() + this->d_length,
5458 newLength - this->d_length,
5461 this->d_length = newLength;
5462 CHAR_TRAITS::assign(*(this->dataPtr() + this->d_length), CHAR_TYPE());
5466template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5467template <
bool ALLOC_PROP>
5469void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::
5470quickSwapExchangeAllocators(basic_string& other,
5473 privateBase().swap(other.privateBase());
5474 AllocatorUtil::swap(&this->allocatorRef(), &other.allocatorRef(),
5478template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5480void basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::
5481 quickSwapRetainAllocators(basic_string& other)
5483 privateBase().swap(other.privateBase());
5487template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5488int basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateCompareRaw(
5489 size_type lhsPosition,
5490 size_type lhsNumChars,
5491 const CHAR_TYPE *other,
5492 size_type otherNumChars)
const
5499 size_type numChars = lhsNumChars < otherNumChars ? lhsNumChars
5501 int cmpResult = CHAR_TRAITS::compare(this->dataPtr() + lhsPosition,
5507 if (lhsNumChars < otherNumChars) {
5510 if (lhsNumChars > otherNumChars) {
5516template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5517template <
class RANGE>
5521basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::privateNumCharsInRange(
5525#if defined(BSLS_LIBRARYFEATURES_HAS_CPP20_CONCEPTS) \
5526 && defined(BSLS_LIBRARYFEATURES_HAS_CPP20_RANGES)
5528 if constexpr (ranges::sized_range<RANGE>) {
5529 return ranges::size(range);
5534 return privateNumCharsInRange(ranges::begin(range),
5535 ranges::end (range));
5538template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5539template <
class INPUT_ITERATOR,
class SENTINEL>
5543 INPUT_ITERATOR first,
5544 SENTINEL last)
const
5546 typedef typename iterator_traits<INPUT_ITERATOR>::iterator_category
5550 : BloombergLP::bslstl::IteratorUtil::insertDistance(first,last);
5557template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5564 CHAR_TRAITS::assign(*
begin(), CHAR_TYPE());
5567template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5570 const ALLOCATOR& basicAllocator)
5573, ContainerBase(basicAllocator)
5575 CHAR_TRAITS::assign(*
begin(), CHAR_TYPE());
5578template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5583, ContainerBase(
AllocatorTraits::select_on_container_copy_construction(
5584 original.get_allocator()))
5590 privateCopyFromOutOfPlaceBuffer(original);
5594template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5598 const ALLOCATOR& basicAllocator)
5600, ContainerBase(basicAllocator)
5606 privateCopyFromOutOfPlaceBuffer(original);
5610template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5613 BloombergLP::bslmf::MovableRef<basic_string> original)
5616, ContainerBase(MoveUtil::access(original).get_allocator())
5618 if (!this->isShortString()) {
5619 basic_string& originalRef = MoveUtil::access(original);
5620 originalRef.resetFields();
5624template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5627 BloombergLP::bslmf::MovableRef<basic_string> original,
5628 const ALLOCATOR& basicAllocator)
5630, ContainerBase(basicAllocator)
5633 basic_string& originalRef = MoveUtil::access(original);
5636 originalRef.resetFields();
5639 privateCopyFromOutOfPlaceBuffer(originalRef);
5644template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5647 BloombergLP::bslmf::MovableRef<basic_string> original,
5649 const ALLOCATOR& basicAllocator)
5651, ContainerBase(basicAllocator)
5653 privateMoveConstruct(MoveUtil::access(original), position);
5656template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5659 BloombergLP::bslmf::MovableRef<basic_string> original,
5662 const ALLOCATOR& basicAllocator)
5664, ContainerBase(basicAllocator)
5666 privateMoveConstruct(MoveUtil::access(original), position, numChars);
5669template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5674 const ALLOCATOR& basicAllocator)
5676, ContainerBase(basicAllocator)
5681template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5687 const ALLOCATOR& basicAllocator)
5689, ContainerBase(basicAllocator)
5691 assign(original, position, numChars);
5694template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5695#ifdef BSLS_COMPILERFEATURES_SUPPORT_CTAD
5700 const CHAR_TYPE *characterString,
5701 const ALLOCATOR& basicAllocator)
5703, ContainerBase(basicAllocator)
5710template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5713 const CHAR_TYPE *characterString,
5715 const ALLOCATOR& basicAllocator)
5717, ContainerBase(basicAllocator)
5721 assign(characterString, numChars);
5724template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5725#ifdef BSLS_COMPILERFEATURES_SUPPORT_CTAD
5731 CHAR_TYPE character,
5732 const ALLOCATOR& basicAllocator)
5734, ContainerBase(basicAllocator)
5736 assign(numChars, character);
5739template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5740template <
class INPUT_ITER>
5745 const ALLOCATOR& basicAllocator)
5747, ContainerBase(basicAllocator)
5752template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5753template <
class RANGE>
5759 const ALLOCATOR& basicAllocator)
5761, ContainerBase(basicAllocator)
5766template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5767template <
class ALLOC2>
5770 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>& original,
5771 const ALLOCATOR& basicAllocator)
5773, ContainerBase(basicAllocator)
5775 this->
assign(original.data(), original.length());
5778template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5781 const BloombergLP::bslstl::StringRefData<CHAR_TYPE>& strRef,
5782 const ALLOCATOR& basicAllocator)
5784, ContainerBase(basicAllocator)
5786 assign(strRef.data(), strRef.length());
5789template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5790template <
class STRING_VIEW_LIKE_TYPE>
5793 const STRING_VIEW_LIKE_TYPE&
object,
5797, ContainerBase(basicAllocator)
5803template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5804template <
class STRING_VIEW_LIKE_TYPE>
5807 const STRING_VIEW_LIKE_TYPE&
object,
5810 const ALLOCATOR& basicAllocator,
5813, ContainerBase(basicAllocator)
5816 privateThrowOutOfRange(
5817 position > strView.
length(),
5818 "string<...>::assign(const string_view&,pos,n): invalid position");
5820 if (numChars > strView.
length() - position) {
5821 numChars = strView.
length() - position;
5827#if defined(BSLS_COMPILERFEATURES_SUPPORT_GENERALIZED_INITIALIZERS)
5828template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5831 std::initializer_list<CHAR_TYPE> values,
5832 const ALLOCATOR& basicAllocator)
5834, ContainerBase(basicAllocator)
5836 append(values.begin(), values.end());
5840template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5848 privateDeallocate();
5849 this->d_length = npos;
5856template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5866 if (Propagate::value) {
5868 quickSwapExchangeAllocators(other, Propagate());
5871 privateAssignDispatch(
5874 "string<...>::operator=(const string&...): string too long");
5880template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5884 BloombergLP::bslmf::MovableRef<basic_string>
rhs)
5886 AllocatorTraits::propagate_on_container_move_assignment::value ||
5887 AllocatorTraits::is_always_equal::value)
5895 if (Propagate::value) {
5897 quickSwapExchangeAllocators(other, Propagate());
5901 quickSwapRetainAllocators(other);
5904 privateAssignDispatch(
5907 "string<...>::operator=(MovableRef<...>): string too long");
5913template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5914template <
class STRING_VIEW_LIKE_TYPE>
5919 const STRING_VIEW_LIKE_TYPE&
rhs)
5922 return privateAssignDispatch(
5925 "string<>::operator=(basic_string_view&): string too long");
5928template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5930basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
5938template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5943 return assign(1, character);
5946template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5947template <
class ALLOC2>
5951 const std::basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOC2>&
rhs)
5953 return privateAssignDispatch(
5956 "string<...>::operator=(std::string&...): string too long");
5959#if defined(BSLS_COMPILERFEATURES_SUPPORT_GENERALIZED_INITIALIZERS)
5960template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5964 std::initializer_list<CHAR_TYPE> values)
5966 return privateAssignDispatch(
5969 "string<...>::operator=(initializer_list): string too long");
5975template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5978 CHAR_TYPE character)
5980 privateThrowLengthError(newLength > max_size(),
5981 "string<...>::resize(n,c): string too long");
5982 privateResizeRaw(newLength, character);
5985template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5989 privateThrowLengthError(newLength > max_size(),
5990 "string<...>::resize(n): string too long");
5991 privateResizeRaw(newLength, CHAR_TYPE());
5994template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
5995template <
class OPERATION>
5998 OPERATION operation)
6000 privateThrowLengthError(newLength > max_size(),
6001 "string<...>::resize_and_overwrite(n, op): string too long");
6003 privateReserveRaw(newLength);
6004 this->d_length = newLength;
6006#ifdef BSLMF_MOVABLEREF_USES_RVALUE_REFERENCES
6008 MoveUtil::move(operation)(this->dataPtr(), newLength));
6011 operation(this->dataPtr(), newLength));
6014 this->d_length = finalLength;
6015 CHAR_TRAITS::assign(*(this->dataPtr() + this->d_length), CHAR_TYPE());
6018template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6023 privateThrowLengthError(newCapacity > max_size(),
6024 "string<...>::reserve(n): string too long");
6025 privateReserveRaw(newCapacity);
6028template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6032 if (this->size() < this->d_capacity) {
6034 temp.privateAppend(this->data(),
6036 "string<...>::shrink_to_fit(): string too long");
6037 quickSwapRetainAllocators(temp);
6041template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6049 privateClear(Imp::BASIC_STRING_DEALLOCATE_IN_CLEAR);
6054template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6059 return this->dataPtr();
6062template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6067 return begin() + this->d_length;
6070template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6078template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6088template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6095 return *(
begin() + position);
6098template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6106 privateThrowOutOfRange(position >= length(),
6107 "string<...>::at(n): invalid position");
6109 return *(
begin() + position);
6112template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6122template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6129 return *(
begin() + length() - 1);
6134template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6143template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6147 const CHAR_TYPE *
rhs)
6154template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6159 push_back(character);
6163template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6164template <
class STRING_VIEW_LIKE_TYPE>
6169 const STRING_VIEW_LIKE_TYPE&
rhs)
6172 return append(strView.
data(),strView.
length());
6175template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6176template <
class ALLOC2>
6178basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
6180 const std::basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOC2>&
rhs)
6182 return append(
rhs.begin(),
rhs.end());
6185template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6191 return append(suffix,
size_type(0), npos);
6194template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6201 privateThrowOutOfRange(
6202 position > suffix.
length(),
6203 "string<...>::append(const string&,pos,n): invalid position");
6205 if (numChars > suffix.
length() - position) {
6206 numChars = suffix.
length() - position;
6208 return privateAppend(
6209 suffix.
data() + position,
6211 "string<...>::append(const string&,pos,n): string too long");
6214template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6218 const CHAR_TYPE *characterString,
6223 return privateAppend(characterString,
6225 "string<...>::append(char*...): string too long");
6228template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6232 const CHAR_TYPE *characterString)
6236 return append(characterString, CHAR_TRAITS::length(characterString));
6239template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6243 CHAR_TYPE character)
6245 return privateAppend(numChars,
6247 "string<...>::append(n,c): string too long");
6250template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6251template <
class STRING_VIEW_LIKE_TYPE>
6256 const STRING_VIEW_LIKE_TYPE& suffix)
6259 return privateAppend(
6262 "string<...>::append(basic_string_view): string too long");
6265template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6266template <
class STRING_VIEW_LIKE_TYPE>
6268 basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>&)
6270 const STRING_VIEW_LIKE_TYPE& suffix,
6275 privateThrowOutOfRange(
6276 position > strView.
length(),
6277 "string<...>::append(basic_string_view,pos,n): invalid position");
6279 if (numChars > strView.
length() - position) {
6280 numChars = strView.
length() - position;
6282 return privateAppend(
6283 strView.
data() + position,
6285 "string<...>::append(basic_string_view,pos,n): string too long");
6288template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6289template <
class INPUT_ITER>
6291basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
6295 return privateAppend(first,
6297 "string<...>::append<Iter>(i,j): string too long");
6300#if defined(BSLS_COMPILERFEATURES_SUPPORT_GENERALIZED_INITIALIZERS)
6301template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6305 std::initializer_list<CHAR_TYPE> values)
6307 return privateAppend(
6310 "string<...>::append(initializer_list): string too long");
6314template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6315template <
class RANGE>
6318basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
6322 size_type numChars = privateNumCharsInRange(range);
6323 return privateAppendRange(ranges::begin(range),
6324 ranges::end (range),
6326 "string<...>::append_range(r): string too long");
6329template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6331 CHAR_TYPE character)
6333 privateThrowLengthError(length() >= max_size(),
6334 "string<...>::push_back(char): string too long");
6336 if (length() + 1 > capacity()) {
6337 privateReserveRaw(length() + 1);
6339 CHAR_TRAITS::assign(*(
begin() + length()), character);
6341 CHAR_TRAITS::assign(*(
begin() + length()), CHAR_TYPE());
6344template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6350 return this->operator=(replacement);
6353template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6357 BloombergLP::bslmf::MovableRef<basic_string> replacement)
6361 return this->operator=(MoveUtil::move(other));
6364template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6371 privateThrowOutOfRange(
6372 position > replacement.
length(),
6373 "string<...>::assign(const string&,pos,n): invalid position");
6375 if (numChars > replacement.
length() - position) {
6376 numChars = replacement.
length() - position;
6378 return privateAssignDispatch(
6379 replacement.
data() + position,
6381 "string<...>::assign(const string&,pos,n): invalid position");
6384template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6388 const CHAR_TYPE *characterString)
6392 return assign(characterString, CHAR_TRAITS::length(characterString));
6395template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6399 const CHAR_TYPE *characterString,
6404 return privateAssignDispatch(
6407 "string<...>::assign(char*...): string too long");
6410template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6411template <
class STRING_VIEW_LIKE_TYPE>
6416 const STRING_VIEW_LIKE_TYPE& replacement)
6420 return this->operator=(strView);
6423template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6424template <
class STRING_VIEW_LIKE_TYPE>
6427 basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>&)
6429 const STRING_VIEW_LIKE_TYPE& replacement,
6435 privateThrowOutOfRange(
6436 position > strView.
length(),
6437 "string<...>::assign(const StrViewLike&,pos,n): invalid position");
6439 if (numChars > strView.
length() - position) {
6440 numChars = strView.
length() - position;
6442 return privateAssignDispatch(
6443 strView.
data() + position,
6445 "string<...>::assign(const StrViewLike&,pos,n): invalid position");
6448template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6449template <
class ALLOC2>
6451basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>&
6453 const std::basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOC2>&
string)
6455 return this->operator=(
string);
6458template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6462 CHAR_TYPE character)
6464 return privateAssignDispatch(numChars,
6466 "string<...>::assign(n,c): string too long");
6469template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6470template <
class INPUT_ITER>
6476 return privateAssignDispatch(
6479 "string<...>::assign<Iter>(i,j): string too long");
6482#if defined(BSLS_COMPILERFEATURES_SUPPORT_GENERALIZED_INITIALIZERS)
6483template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6487 std::initializer_list<CHAR_TYPE> values)
6489 return privateAssignDispatch(
6492 "string<...>::assign(initializer_list): string too long");
6496template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6497template <
class RANGE>
6500basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
6504 size_type numChars = privateNumCharsInRange(range);
6505 return privateAssignRangeDispatch(
6506 ranges::begin(range),
6507 ranges::end (range),
6509 "string<...>::assign<Range>(r): string too long");
6512template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6519 return insert(position, other,
size_type(0), npos);
6522template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6530 privateThrowOutOfRange(
6531 position > length(),
6532 "string<...>::insert(pos,const string&...): invalid position");
6533 privateThrowOutOfRange(
6534 sourcePosition > other.
length(),
6535 "string<...>::insert(pos,const string&...): invalid source position");
6537 if (numChars > other.
length() - sourcePosition) {
6538 numChars = other.
length() - sourcePosition;
6540 privateThrowLengthError(
6541 numChars > max_size() - length(),
6542 "string<...>::insert(pos,const string&...): string too long");
6543 return privateInsertRaw(position, other.
data() + sourcePosition, numChars);
6546template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6550 const CHAR_TYPE *characterString,
6555 privateThrowOutOfRange(
6556 position > length(),
6557 "string<...>::insert(pos,char*...): invalid position");
6559 privateThrowLengthError(
6560 numChars > max_size() - length(),
6561 "string<...>::insert(pos,char*...): string too long");
6562 return privateInsertRaw(position, characterString, numChars);
6565template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6570 const CHAR_TYPE *characterString)
6574 return insert(position,
6576 CHAR_TRAITS::length(characterString));
6579template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6583 CHAR_TYPE character)
6585 privateThrowOutOfRange(position > length(),
6586 "string<...>::insert(pos,n,c): invalid position");
6588 privateThrowLengthError(numChars > max_size() - length(),
6589 "string<...>::insert(pos,n,c): string too long");
6590 return privateReplaceRaw(position,
size_type(0), numChars, character);
6593template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6596 CHAR_TYPE character)
6603 return begin() + pos;
6606#if defined(BSLS_PLATFORM_CMP_SUN) && BSLS_PLATFORM_CMP_VERSION < 0x5130
6614# define BSLSTL_INSERT_RETURN_TYPE CHAR_TYPE *
6616# define BSLSTL_INSERT_RETURN_TYPE \
6617 typename basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::iterator
6620template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6621template <
class INPUT_ITER>
6632 privateInsertDispatch(position, first, last);
6633 return begin() + pos;
6636template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6641 CHAR_TYPE character)
6647 insert(pos, numChars, character);
6648 return begin() + pos;
6651template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6652template <
class STRING_VIEW_LIKE_TYPE>
6657 const STRING_VIEW_LIKE_TYPE& other)
6660 privateThrowOutOfRange(
6661 position > length(),
6662 "string<...>::insert(pos,const string_view&): invalid position");
6663 privateThrowLengthError(
6664 strView.
length() > max_size() - length(),
6665 "string<...>::insert(pos,const string_view&): string too long");
6666 return privateInsertRaw(position, strView.
data(), strView.
length());
6669template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6670template <
class STRING_VIEW_LIKE_TYPE>
6672 basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>&)
6673basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>::insert(
6675 const STRING_VIEW_LIKE_TYPE& other,
6676 size_type sourcePosition,
6680 privateThrowOutOfRange(
6681 position > length(),
6682 "string<...>::insert(pos,const string_view&...): invalid position");
6683 privateThrowOutOfRange(sourcePosition > strView.
length(),
6684 "string<...>::insert(pos,const string_view&...): "
6685 "invalid source position");
6687 if (numChars > strView.
length() - sourcePosition) {
6688 numChars = strView.
length() - sourcePosition;
6690 privateThrowLengthError(
6691 numChars > max_size() - length(),
6692 "string<...>::insert(pos,const string&...): string too long");
6693 return privateInsertRaw(position,
6694 strView.
data() + sourcePosition,
6698#if defined(BSLS_COMPILERFEATURES_SUPPORT_GENERALIZED_INITIALIZERS)
6699template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6702basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>::insert(
6703 const_iterator position,
6704 std::initializer_list<CHAR_TYPE> values)
6709 size_type pos = position -
cbegin();
6710 privateInsertDispatch(position, values.begin(), values.end());
6711 return begin() + pos;
6715template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6716template <
class RANGE>
6728 size_type inNumChars = privateNumCharsInRange(range);
6729 privateInsertRange(position,
6731 ranges::begin(range),
6732 ranges:: end(range));
6733 return begin() + pos;
6736#undef BSLSTL_INSERT_RETURN_TYPE
6738template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6743 privateThrowOutOfRange(position > length(),
6744 "string<...>::erase(pos,n): invalid position");
6746 if (numChars > length() - position) {
6747 numChars = length() - position;
6750 this->d_length -= numChars;
6751 CHAR_TRAITS::move(this->dataPtr() + position,
6752 this->dataPtr() + position + numChars,
6753 this->d_length - position);
6754 CHAR_TRAITS::assign(*(
begin() + length()), CHAR_TYPE());
6759template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6770 CHAR_TRAITS::move(&*dstPosition, &*postPosition,
cend() - postPosition);
6773 CHAR_TRAITS::assign(*(this->dataPtr() + length()), CHAR_TYPE());
6778template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6791 if (first != last) {
6792 CHAR_TRAITS::move(&*dstFirst, &*last,
cend() - last);
6794 this->d_length -= last - first;
6795 CHAR_TRAITS::assign(*(this->dataPtr() + length()), CHAR_TYPE());
6801template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6808 CHAR_TRAITS::assign(*(
begin() + length()), CHAR_TYPE());
6811template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6818 privateThrowOutOfRange(
6819 length() < outPosition,
6820 "string<...>::replace(pos,const string&...): invalid position");
6821 if (outNumChars > length() - outPosition) {
6822 outNumChars = length() - outPosition;
6824 privateThrowLengthError(
6825 replacement.
length() > outNumChars &&
6826 replacement.
length() - outNumChars > max_size() - length(),
6827 "string<...>::replace(pos,const string&...): string too long");
6828 return privateReplaceRaw(outPosition,
6834template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6843 privateThrowOutOfRange(
6844 length() < outPosition,
6845 "string<...>::replace(pos,const string&...): invalid position");
6847 if (outNumChars > length() - outPosition) {
6848 outNumChars = length() - outPosition;
6850 privateThrowOutOfRange(
6851 position > replacement.
length(),
6852 "string<...>::replace(pos,const string&...): invalid position");
6854 if (numChars > replacement.
length() - position) {
6855 numChars = replacement.
length() - position;
6857 privateThrowLengthError(
6858 numChars > outNumChars &&
6859 numChars - outNumChars > max_size() - length(),
6860 "string<...>::replace(pos,const string&...): string too long");
6861 return privateReplaceRaw(outPosition,
6863 replacement.
data() + position,
6867template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6872 const CHAR_TYPE *characterString,
6877 privateThrowOutOfRange(
6878 length() < outPosition,
6879 "string<...>::replace(pos,char*...): invalid position");
6881 if (outNumChars > length() - outPosition) {
6882 outNumChars = length() - outPosition;
6885 privateThrowLengthError(
6886 numChars > outNumChars &&
6887 numChars - outNumChars > max_size() - length(),
6888 "string<...>::replace(pos,char*...): string too long");
6889 return privateReplaceRaw(outPosition,
6895template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6901 const CHAR_TYPE *characterString)
6905 return replace(outPosition,
6908 CHAR_TRAITS::length(characterString));
6911template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6916 CHAR_TYPE character)
6918 privateThrowOutOfRange(
6919 length() < outPosition,
6920 "string<...>::replace(pos,n,c): invalid position");
6921 if (outNumChars > length() - outPosition) {
6922 outNumChars = length() - outPosition;
6924 privateThrowLengthError(
6925 numChars > outNumChars &&
6926 numChars - outNumChars > max_size() - length(),
6927 "string<...>::replace(pos,n,c): string too long");
6928 return privateReplaceRaw(outPosition,
6934template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6935template <
class STRING_VIEW_LIKE_TYPE>
6939 size_type outPosition,
6940 size_type outNumChars,
6941 const STRING_VIEW_LIKE_TYPE& replacement)
6943 privateThrowOutOfRange(
6944 length() < outPosition,
6945 "string<...>::replace(pos,const strView&...): invalid position");
6946 if (outNumChars > length() - outPosition) {
6947 outNumChars = length() - outPosition;
6951 privateThrowLengthError(
6952 strView.
length() > outNumChars &&
6953 strView.
length() - outNumChars > max_size() - length(),
6954 "string<...>::replace(pos,const strView&...): string too long");
6955 return privateReplaceRaw(outPosition,
6961template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6962template <
class STRING_VIEW_LIKE_TYPE>
6964 basic_string<CHAR_TYPE, CHAR_TRAITS, ALLOCATOR>&)
6966 size_type outPosition,
6967 size_type outNumChars,
6968 const STRING_VIEW_LIKE_TYPE& replacement,
6972 privateThrowOutOfRange(
6973 length() < outPosition,
6974 "string<...>::replace(pos,const strView&...): invalid position");
6976 if (outNumChars > length() - outPosition) {
6977 outNumChars = length() - outPosition;
6981 privateThrowOutOfRange(
6982 position > strView.
length(),
6983 "string<...>::replace(pos,const strView&...): invalid position");
6985 if (numChars > strView.
length() - position) {
6986 numChars = strView.
length() - position;
6988 privateThrowLengthError(
6989 numChars > outNumChars &&
6990 numChars - outNumChars > max_size() - length(),
6991 "string<...>::replace(pos,const strView&...): string too long");
6992 return privateReplaceRaw(outPosition,
6994 strView.
data() + position,
6998template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
6999basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
7013 privateThrowLengthError(
7014 replacement.
length() > outNumChars &&
7015 replacement.
length() - outNumChars > max_size() - length(),
7016 "string<...>::replace(const string&...): string too long");
7018 return privateReplaceRaw(outPosition,
7024template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7025template <
class STRING_VIEW_LIKE_TYPE>
7029 const_iterator first,
7030 const_iterator last,
7031 const STRING_VIEW_LIKE_TYPE& replacement)
7038 size_type outPosition = first -
cbegin();
7039 size_type outNumChars = last - first;
7042 privateThrowLengthError(
7043 strView.
length() > outNumChars &&
7044 strView.
length() - outNumChars > max_size() - length(),
7045 "string<...>::replace(const strView&...): string too long");
7047 return privateReplaceRaw(outPosition,
7053template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7054basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>&
7058 const CHAR_TYPE *characterString,
7069 privateThrowLengthError(
7070 numChars > outNumChars &&
7071 numChars - outNumChars > max_size() - length(),
7072 "string<...>::replace(char*...): string too long");
7073 return privateReplaceRaw(outPosition,
7079template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7085 const CHAR_TYPE *characterString)
7093 return replace(first,
7096 CHAR_TRAITS::length(characterString));
7099template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7105 CHAR_TYPE character)
7114 privateThrowLengthError(numChars > outNumChars &&
7115 numChars - outNumChars > max_size() - length(),
7116 "string<...>::replace(n,c): string too long");
7117 return privateReplaceRaw(outPosition, outNumChars, numChars, character);
7120template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7121template <
class INPUT_ITER>
7127 INPUT_ITER stringFirst,
7128 INPUT_ITER stringLast)
7137 return privateReplaceDispatch(outPosition,
7142 BloombergLP::bslmf::Nil());
7145template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7146template <
class RANGE>
7162 size_type inNumChars = privateNumCharsInRange(range);
7164 return privateReplaceRange(outPosition,
7167 ranges::begin(range),
7168 ranges:: end(range));
7174template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7179 return this->dataPtr();
7182template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7186 AllocatorTraits::propagate_on_container_swap::value ||
7187 AllocatorTraits::is_always_equal::value)
7190 AllocatorTraits::propagate_on_container_swap Propagate;
7192 if (Propagate::value) {
7193 quickSwapExchangeAllocators(other, Propagate());
7196 get_allocator() == other.get_allocator())) {
7197 quickSwapRetainAllocators(other);
7202 basic_string toThisCopy(MoveUtil::move(other), get_allocator());
7203 basic_string toOtherCopy(MoveUtil::move(*
this),
7204 other.get_allocator());
7206 this->quickSwapRetainAllocators(toThisCopy);
7207 other.quickSwapRetainAllocators(toOtherCopy);
7215template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7221 return this->dataPtr();
7224template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7233template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7239 return begin() + this->d_length;
7242template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7251template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7260template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7269template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7278template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7289template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7295 return this->d_length;
7298template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7304 return this->d_length;
7307template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7316 size_type allocMaxSize = AllocatorTraits::max_size(get_allocator()) - 1;
7317 return allocMaxSize < stringMaxSize ? allocMaxSize : stringMaxSize;
7320template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7326 return this->d_capacity;
7329template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7334 return this->d_length == 0;
7339template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7347 return *(
begin() + position);
7350template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7357 privateThrowOutOfRange(position >= length(),
7358 "const string<...>::at(n): invalid position");
7359 return *(
begin() + position);
7362template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7372template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7379 return *(
end() - 1);
7382template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7390 privateThrowOutOfRange(
7391 length() < position,
7392 "const string<...>::copy(str,pos,n): invalid position");
7393 if (numChars > length() - position) {
7394 numChars = length() - position;
7396 CHAR_TRAITS::move(characterString, this->dataPtr() + position, numChars);
7402template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7408 return this->dataPtr();
7411template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7417 return this->dataPtr();
7420template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7426 return this->allocatorRef();
7429template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7437 return find(substring.data(), position, substring.length());
7440template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7441template <
class STRING_VIEW_LIKE_TYPE>
7445 const STRING_VIEW_LIKE_TYPE& substring,
7451 return find(strView.
data(), position, strView.
length());
7454template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7457 const CHAR_TYPE *substring,
7463 size_type remChars = length() - position;
7464 if (position > length() || numChars > remChars) {
7467 if (0 == numChars) {
7470 const CHAR_TYPE *thisString = this->dataPtr() + position;
7471 const CHAR_TYPE *nextString;
7472 for (remChars -= numChars - 1;
7473 0 != (nextString = BSLSTL_CHAR_TRAITS::find(thisString,
7476 remChars -= ++nextString - thisString, thisString = nextString)
7478 if (0 == CHAR_TRAITS::compare(nextString, substring, numChars)) {
7479 return nextString - this->dataPtr();
7485template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7489 const CHAR_TYPE *substring,
7494 return find(substring, position, CHAR_TRAITS::length(substring));
7497template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7502 if (position >= length()) {
7505 const CHAR_TYPE *result =
7506 BSLSTL_CHAR_TRAITS::find(this->dataPtr() + position,
7507 length() - position,
7509 return result ? result - this->dataPtr() : npos;
7512template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7520 return rfind(substring.data(), position, substring.length());
7523template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7524template <
class STRING_VIEW_LIKE_TYPE>
7528 const STRING_VIEW_LIKE_TYPE& substring,
7534 return rfind(strView.
data(), position, strView.
length());
7537template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7540 const CHAR_TYPE *characterString,
7546 if (0 == numChars) {
7547 return position > length() ? length() : position;
7549 if (numChars <= length()) {
7550 if (position > length() - numChars) {
7551 position = length() - numChars;
7553 const CHAR_TYPE *thisString = this->dataPtr() + position;
7554 for (; position != npos; --thisString, --position) {
7555 if (0 == CHAR_TRAITS::compare(thisString,
7565template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7569 const CHAR_TYPE *characterString,
7574 return rfind(characterString,
7576 CHAR_TRAITS::length(characterString));
7579template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7585 return rfind(&character, position,
size_type(1));
7588template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7596 return find_first_of(characterString.data(),
7598 characterString.length());
7601template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7602template <
class STRING_VIEW_LIKE_TYPE>
7606 const STRING_VIEW_LIKE_TYPE& characterString,
7612 return find_first_of(strView.
data(), position, strView.
length());
7615template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7618 const CHAR_TYPE *characterString,
7624 if (0 < numChars && position < length()) {
7625 for (
const CHAR_TYPE *current = this->dataPtr() + position;
7626 current != this->dataPtr() + length();
7629 if (BSLSTL_CHAR_TRAITS::find(characterString, numChars, *current)
7631 return current - this->dataPtr();
7638template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7642 const CHAR_TYPE *characterString,
7647 return find_first_of(characterString,
7649 CHAR_TRAITS::length(characterString));
7652template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7656 CHAR_TYPE character,
7659 return find_first_of(&character, position,
size_type(1));
7662template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7670 return find_last_of(characterString.data(),
7672 characterString.length());
7675template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7676template <
class STRING_VIEW_LIKE_TYPE>
7680 const STRING_VIEW_LIKE_TYPE& characterString,
7686 return find_last_of(strView.
data(), position, strView.
length());
7689template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7692 const CHAR_TYPE *characterString,
7698 if (0 < numChars && 0 < length()) {
7699 size_type remChars = position < length() ? position : length() - 1;
7700 for (
const CHAR_TYPE *current = this->dataPtr() + remChars;
7704 if (BSLSTL_CHAR_TRAITS::find(
7705 characterString, numChars, *current)) {
7706 return current - this->dataPtr();
7708 if (current == this->dataPtr()) {
7716template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7720 const CHAR_TYPE *characterString,
7725 return find_last_of(characterString,
7727 CHAR_TRAITS::length(characterString));
7730template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7734 CHAR_TYPE character,
7737 return find_last_of(&character, position,
size_type(1));
7740template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7748 return find_first_not_of(characterString.data(),
7750 characterString.length());
7753template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7754template <
class STRING_VIEW_LIKE_TYPE>
7758 const STRING_VIEW_LIKE_TYPE& characterString,
7764 return find_first_not_of(strView.
data(), position, strView.
length());
7767template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7770 const CHAR_TYPE *characterString,
7776 if (position < length()) {
7777 const CHAR_TYPE *last = this->dataPtr() + length();
7778 for (
const CHAR_TYPE *current = this->dataPtr() + position;
7782 if (!BSLSTL_CHAR_TRAITS::find(
7783 characterString, numChars, *current)) {
7784 return current - this->dataPtr();
7791template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7795 const CHAR_TYPE *characterString,
7800 return find_first_not_of(characterString,
7802 CHAR_TRAITS::length(characterString));
7805template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7809 CHAR_TYPE character,
7812 return find_first_not_of(&character, position,
size_type(1));
7815template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7823 return find_last_not_of(characterString.data(),
7825 characterString.length());
7828template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7829template <
class STRING_VIEW_LIKE_TYPE>
7833 const STRING_VIEW_LIKE_TYPE& characterString,
7839 return find_last_not_of(strView.
data(), position, strView.
length());
7842template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7845 const CHAR_TYPE *characterString,
7852 size_type remChars = position < length() ? position : length() - 1;
7853 for (
const CHAR_TYPE *current = this->dataPtr() + remChars;
7855 --current, --remChars)
7857 if (!BSLSTL_CHAR_TRAITS::find(
7858 characterString, numChars, *current)) {
7859 return current - this->dataPtr();
7866template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7870 const CHAR_TYPE *characterString,
7875 return find_last_not_of(characterString,
7877 CHAR_TRAITS::length(characterString));
7880template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7884 CHAR_TYPE character,
7887 return find_last_not_of(&character, position,
size_type(1));
7890template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7896 return npos != find(subview);
7899template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7904 return npos != find(character);
7907template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7910 const CHAR_TYPE* characterString)
const
7913 return npos != find(characterString);
7916template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7922 return (length() >= characterString.length() &&
7923 0 == CHAR_TRAITS::compare(
data(),
7924 characterString.data(),
7925 characterString.size()));
7928template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7933 return (0 < length() && CHAR_TRAITS::eq(*
data(), character));
7936template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7939 const CHAR_TYPE *characterString)
const
7943 std::size_t strLength = CHAR_TRAITS::length(characterString);
7944 return (length() >= strLength &&
7945 0 == CHAR_TRAITS::compare(
data(),
7950template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7956 return (length() >= characterString.length() &&
7957 0 == CHAR_TRAITS::compare(
7958 data() + length() - characterString.length(),
7959 characterString.data(),
7960 characterString.size()));
7963template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7968 return (0 < length() &&
7969 CHAR_TRAITS::eq(*(
data()+ length() - 1), character));
7972template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7975 const CHAR_TYPE *characterString)
const
7979 std::size_t strLength = CHAR_TRAITS::length(characterString);
7980 return (length() >= strLength &&
7981 0 == CHAR_TRAITS::compare(
data() + length() - strLength,
7986#ifdef BSLS_COMPILERFEATURES_SUPPORT_REF_QUALIFIERS
7987template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
7992 size_type numChars)
const &
7996 ALLOCATOR>(*
this, position, numChars);
7999template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8001basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>
8003 size_type numChars) &&
8005 return basic_string<CHAR_TYPE,
8007 ALLOCATOR>(MoveUtil::move(*
this), position, numChars);
8010template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8012basic_string<CHAR_TYPE,CHAR_TRAITS,ALLOCATOR>
8018 ALLOCATOR>(*
this, position, numChars);
8022template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8034template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8040 privateThrowOutOfRange(
8041 length() < position,
8042 "const string<...>::compare(pos,n,...): invalid position");
8043 if (numChars > length() - position) {
8044 numChars = length() - position;
8046 return privateCompareRaw(position, numChars, other.
data(), other.
length());
8049template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8057 privateThrowOutOfRange(
8058 length() < lhsPosition,
8059 "const string<...>::compare(pos,n,...): invalid position");
8060 if (lhsNumChars > length() - lhsPosition) {
8061 lhsNumChars = length() - lhsPosition;
8063 privateThrowOutOfRange(
8064 other.
length() < otherPosition,
8065 "const string<...>::compare(pos,n,...): invalid position");
8066 if (otherNumChars > other.
length() - otherPosition) {
8067 otherNumChars = other.
length() - otherPosition;
8069 return privateCompareRaw(lhsPosition,
8071 other.dataPtr() + otherPosition,
8075template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8078 const CHAR_TYPE *other)
const
8085 CHAR_TRAITS::length(other));
8088template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8092 const CHAR_TYPE *other,
8097 privateThrowOutOfRange(
8098 length() < lhsPosition,
8099 "const string<...>::compare(pos,n,...): invalid position");
8100 if (lhsNumChars > length() - lhsPosition) {
8101 lhsNumChars = length() - lhsPosition;
8103 return privateCompareRaw(lhsPosition,
8109template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8114 const CHAR_TYPE *other)
const
8118 return compare(lhsPosition,
8121 CHAR_TRAITS::length(other));
8124template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8125template <
class STRING_VIEW_LIKE_TYPE>
8128 const STRING_VIEW_LIKE_TYPE& other,
8140template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8141template <
class STRING_VIEW_LIKE_TYPE>
8145 const STRING_VIEW_LIKE_TYPE& other,
8148 privateThrowOutOfRange(
8149 length() < position,
8150 "string<...>::compare(pos,n,StrViewLike): invalid position");
8154 if (numChars > length() - position) {
8155 numChars = length() - position;
8157 return privateCompareRaw(position,
8163template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>
8164template <
class STRING_VIEW_LIKE_TYPE>
8168 const STRING_VIEW_LIKE_TYPE& other,
8173 privateThrowOutOfRange(
8174 length() < lhsPosition,
8175 "string<...>::compare(pos,n, StrViewLike,...): invalid lhs position");
8179 privateThrowOutOfRange(
8180 strView.
length() < otherPosition,
8181 "string<...>::compare(pos,n, StrViewLike,...): invalid rhs position");
8183 if (lhsNumChars > length() - lhsPosition) {
8184 lhsNumChars = length() - lhsPosition;
8186 if (otherNumChars > other.length() - otherPosition) {
8187 otherNumChars = other.length() - otherPosition;
8189 return privateCompareRaw(lhsPosition,
8191 strView.
data() + otherPosition,
8195template <
class CHAR_TYPE,
class CHAR_TRAITS,
class ALLOCATOR>