Bug Summary

File:home/fedora/workspace/kea-dev/clang-static-analyzer/src/lib/dhcp/option_space.cc
Warning:line 45, column 1
Potential memory leak

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-redhat-linux-gnu -analyze -disable-free -clear-ast-before-backend -disable-llvm-verifier -discard-value-names -main-file-name option_space.cc -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=cplusplus -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -fhalf-no-semantic-interposition -mframe-pointer=all -fmath-errno -ffp-contract=on -fno-rounding-math -mconstructor-aliases -funwind-tables=2 -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -fcoverage-compilation-dir=/home/fedora/workspace/kea-dev/clang-static-analyzer/src/lib/dhcp -resource-dir /usr/lib64/clang/16 -D HAVE_CONFIG_H -I . -I ../../.. -I ../../../src/lib -I ../../../src/lib -D OS_LINUX -I ../../.. -I ../../.. -D PIC -internal-isystem /usr/bin/../lib/gcc/x86_64-redhat-linux/13/../../../../include/c++/13 -internal-isystem /usr/bin/../lib/gcc/x86_64-redhat-linux/13/../../../../include/c++/13/x86_64-redhat-linux -internal-isystem /usr/bin/../lib/gcc/x86_64-redhat-linux/13/../../../../include/c++/13/backward -internal-isystem /usr/lib64/clang/16/include -internal-isystem /usr/local/include -internal-isystem /usr/bin/../lib/gcc/x86_64-redhat-linux/13/../../../../x86_64-redhat-linux/include -internal-externc-isystem /include -internal-externc-isystem /usr/include -O0 -Wwrite-strings -Wno-sign-compare -Wno-missing-field-initializers -std=c++20 -fdeprecated-macro -fdebug-compilation-dir=/home/fedora/workspace/kea-dev/clang-static-analyzer/src/lib/dhcp -ferror-limit 19 -stack-protector 2 -fgnuc-version=4.2.1 -fno-implicit-modules -fcxx-exceptions -fexceptions -analyzer-output=html -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /home/fedora/workspace/kea-dev/clang-static-analyzer/report/2024-05-17-164749-18469-1 -x c++ option_space.cc

option_space.cc

1// Copyright (C) 2012-2015 Internet Systems Consortium, Inc. ("ISC")
2//
3// This Source Code Form is subject to the terms of the Mozilla Public
4// License, v. 2.0. If a copy of the MPL was not distributed with this
5// file, You can obtain one at http://mozilla.org/MPL/2.0/.
6
7#include <config.h>
8
9#include <dhcp/option_space.h>
10#include <boost/algorithm/string/classification.hpp>
11#include <boost/algorithm/string/predicate.hpp>
12
13namespace isc {
14namespace dhcp {
15
16OptionSpace::OptionSpace(const std::string& name, const bool vendor_space)
17 : name_(name), vendor_space_(vendor_space) {
18 // Check that provided option space name is valid.
19 if (!validateName(name_)) {
2
Calling 'OptionSpace::validateName'
20 isc_throw(InvalidOptionSpace, "Invalid option space name "do { std::ostringstream oss__; oss__ << "Invalid option space name "
<< name_; throw InvalidOptionSpace("option_space.cc", 21
, oss__.str().c_str()); } while (1)
21 << name_)do { std::ostringstream oss__; oss__ << "Invalid option space name "
<< name_; throw InvalidOptionSpace("option_space.cc", 21
, oss__.str().c_str()); } while (1)
;
22 }
23}
24
25bool
26OptionSpace::validateName(const std::string& name) {
27
28 using namespace boost::algorithm;
29
30 // Allowed characters are: lower or upper case letters, digits,
31 // underscores and hyphens. Empty option spaces are not allowed.
32 if (all(name, boost::is_from_range('a', 'z') ||
10
Taking true branch
33 boost::is_from_range('A', 'Z') ||
34 boost::is_digit() ||
35 boost::is_any_of(std::string("-_"))) &&
36 !name.empty() &&
3
Assuming the condition is true
37 // Hyphens and underscores are not allowed at the beginning
38 // and at the end of the option space name.
39 !all(find_head(name, 1), boost::is_any_of(std::string("-_"))) &&
40 !all(find_tail(name, 1), boost::is_any_of(std::string("-_")))) {
4
Calling 'is_any_of<std::basic_string<char>>'
9
Returned allocated memory
41 return (true);
42
43 }
44 return (false);
45}
11
Potential memory leak
46
47OptionSpace6::OptionSpace6(const std::string& name)
48 : OptionSpace(name),
49 enterprise_number_(0) {
50}
51
52OptionSpace6::OptionSpace6(const std::string& name,
53 const uint32_t enterprise_number)
54 : OptionSpace(name, true),
1
Calling constructor for 'OptionSpace'
55 enterprise_number_(enterprise_number) {
56}
57
58void
59OptionSpace6::setVendorSpace(const uint32_t enterprise_number) {
60 enterprise_number_ = enterprise_number;
61 OptionSpace::setVendorSpace();
62}
63
64} // end of isc::dhcp namespace
65} // end of isc namespace

/usr/include/boost/algorithm/string/classification.hpp

1// Boost string_algo library classification.hpp header file ---------------------------//
2
3// Copyright Pavol Droba 2002-2003.
4//
5// Distributed under the Boost Software License, Version 1.0.
6// (See accompanying file LICENSE_1_0.txt or copy at
7// http://www.boost.org/LICENSE_1_0.txt)
8
9// See http://www.boost.org/ for updates, documentation, and revision history.
10
11#ifndef BOOST_STRING_CLASSIFICATION_HPP
12#define BOOST_STRING_CLASSIFICATION_HPP
13
14#include <algorithm>
15#include <locale>
16#include <boost/range/value_type.hpp>
17#include <boost/range/as_literal.hpp>
18#include <boost/algorithm/string/detail/classification.hpp>
19#include <boost/algorithm/string/predicate_facade.hpp>
20
21
22/*! \file
23 Classification predicates are included in the library to give
24 some more convenience when using algorithms like \c trim() and \c all().
25 They wrap functionality of STL classification functions ( e.g. \c std::isspace() )
26 into generic functors.
27*/
28
29namespace boost {
30 namespace algorithm {
31
32// classification functor generator -------------------------------------//
33
34 //! is_classified predicate
35 /*!
36 Construct the \c is_classified predicate. This predicate holds if the input is
37 of specified \c std::ctype category.
38
39 \param Type A \c std::ctype category
40 \param Loc A locale used for classification
41 \return An instance of the \c is_classified predicate
42 */
43 inline detail::is_classifiedF
44 is_classified(std::ctype_base::mask Type, const std::locale& Loc=std::locale())
45 {
46 return detail::is_classifiedF(Type, Loc);
47 }
48
49 //! is_space predicate
50 /*!
51 Construct the \c is_classified predicate for the \c ctype_base::space category.
52
53 \param Loc A locale used for classification
54 \return An instance of the \c is_classified predicate
55 */
56 inline detail::is_classifiedF
57 is_space(const std::locale& Loc=std::locale())
58 {
59 return detail::is_classifiedF(std::ctype_base::space, Loc);
60 }
61
62 //! is_alnum predicate
63 /*!
64 Construct the \c is_classified predicate for the \c ctype_base::alnum category.
65
66 \param Loc A locale used for classification
67 \return An instance of the \c is_classified predicate
68 */
69 inline detail::is_classifiedF
70 is_alnum(const std::locale& Loc=std::locale())
71 {
72 return detail::is_classifiedF(std::ctype_base::alnum, Loc);
73 }
74
75 //! is_alpha predicate
76 /*!
77 Construct the \c is_classified predicate for the \c ctype_base::alpha category.
78
79 \param Loc A locale used for classification
80 \return An instance of the \c is_classified predicate
81 */
82 inline detail::is_classifiedF
83 is_alpha(const std::locale& Loc=std::locale())
84 {
85 return detail::is_classifiedF(std::ctype_base::alpha, Loc);
86 }
87
88 //! is_cntrl predicate
89 /*!
90 Construct the \c is_classified predicate for the \c ctype_base::cntrl category.
91
92 \param Loc A locale used for classification
93 \return An instance of the \c is_classified predicate
94 */
95 inline detail::is_classifiedF
96 is_cntrl(const std::locale& Loc=std::locale())
97 {
98 return detail::is_classifiedF(std::ctype_base::cntrl, Loc);
99 }
100
101 //! is_digit predicate
102 /*!
103 Construct the \c is_classified predicate for the \c ctype_base::digit category.
104
105 \param Loc A locale used for classification
106 \return An instance of the \c is_classified predicate
107 */
108 inline detail::is_classifiedF
109 is_digit(const std::locale& Loc=std::locale())
110 {
111 return detail::is_classifiedF(std::ctype_base::digit, Loc);
112 }
113
114 //! is_graph predicate
115 /*!
116 Construct the \c is_classified predicate for the \c ctype_base::graph category.
117
118 \param Loc A locale used for classification
119 \return An instance of the \c is_classified predicate
120 */
121 inline detail::is_classifiedF
122 is_graph(const std::locale& Loc=std::locale())
123 {
124 return detail::is_classifiedF(std::ctype_base::graph, Loc);
125 }
126
127 //! is_lower predicate
128 /*!
129 Construct the \c is_classified predicate for the \c ctype_base::lower category.
130
131 \param Loc A locale used for classification
132 \return An instance of \c is_classified predicate
133 */
134 inline detail::is_classifiedF
135 is_lower(const std::locale& Loc=std::locale())
136 {
137 return detail::is_classifiedF(std::ctype_base::lower, Loc);
138 }
139
140 //! is_print predicate
141 /*!
142 Construct the \c is_classified predicate for the \c ctype_base::print category.
143
144 \param Loc A locale used for classification
145 \return An instance of the \c is_classified predicate
146 */
147 inline detail::is_classifiedF
148 is_print(const std::locale& Loc=std::locale())
149 {
150 return detail::is_classifiedF(std::ctype_base::print, Loc);
151 }
152
153 //! is_punct predicate
154 /*!
155 Construct the \c is_classified predicate for the \c ctype_base::punct category.
156
157 \param Loc A locale used for classification
158 \return An instance of the \c is_classified predicate
159 */
160 inline detail::is_classifiedF
161 is_punct(const std::locale& Loc=std::locale())
162 {
163 return detail::is_classifiedF(std::ctype_base::punct, Loc);
164 }
165
166 //! is_upper predicate
167 /*!
168 Construct the \c is_classified predicate for the \c ctype_base::upper category.
169
170 \param Loc A locale used for classification
171 \return An instance of the \c is_classified predicate
172 */
173 inline detail::is_classifiedF
174 is_upper(const std::locale& Loc=std::locale())
175 {
176 return detail::is_classifiedF(std::ctype_base::upper, Loc);
177 }
178
179 //! is_xdigit predicate
180 /*!
181 Construct the \c is_classified predicate for the \c ctype_base::xdigit category.
182
183 \param Loc A locale used for classification
184 \return An instance of the \c is_classified predicate
185 */
186 inline detail::is_classifiedF
187 is_xdigit(const std::locale& Loc=std::locale())
188 {
189 return detail::is_classifiedF(std::ctype_base::xdigit, Loc);
190 }
191
192 //! is_any_of predicate
193 /*!
194 Construct the \c is_any_of predicate. The predicate holds if the input
195 is included in the specified set of characters.
196
197 \param Set A set of characters to be recognized
198 \return An instance of the \c is_any_of predicate
199 */
200 template<typename RangeT>
201 inline detail::is_any_ofF<
202 BOOST_STRING_TYPENAMEtypename range_value<RangeT>::type>
203 is_any_of( const RangeT& Set )
204 {
205 iterator_range<BOOST_STRING_TYPENAMEtypename range_const_iterator<RangeT>::type> lit_set(boost::as_literal(Set));
206 return detail::is_any_ofF<BOOST_STRING_TYPENAMEtypename range_value<RangeT>::type>(lit_set);
5
Calling constructor for 'is_any_ofF<char>'
8
Returning from constructor for 'is_any_ofF<char>'
207 }
208
209 //! is_from_range predicate
210 /*!
211 Construct the \c is_from_range predicate. The predicate holds if the input
212 is included in the specified range. (i.e. From <= Ch <= To )
213
214 \param From The start of the range
215 \param To The end of the range
216 \return An instance of the \c is_from_range predicate
217 */
218 template<typename CharT>
219 inline detail::is_from_rangeF<CharT> is_from_range(CharT From, CharT To)
220 {
221 return detail::is_from_rangeF<CharT>(From,To);
222 }
223
224 // predicate combinators ---------------------------------------------------//
225
226 //! predicate 'and' composition predicate
227 /*!
228 Construct the \c class_and predicate. This predicate can be used
229 to logically combine two classification predicates. \c class_and holds,
230 if both predicates return true.
231
232 \param Pred1 The first predicate
233 \param Pred2 The second predicate
234 \return An instance of the \c class_and predicate
235 */
236 template<typename Pred1T, typename Pred2T>
237 inline detail::pred_andF<Pred1T, Pred2T>
238 operator&&(
239 const predicate_facade<Pred1T>& Pred1,
240 const predicate_facade<Pred2T>& Pred2 )
241 {
242 // Doing the static_cast with the pointer instead of the reference
243 // is a workaround for some compilers which have problems with
244 // static_cast's of template references, i.e. CW8. /grafik/
245 return detail::pred_andF<Pred1T,Pred2T>(
246 *static_cast<const Pred1T*>(&Pred1),
247 *static_cast<const Pred2T*>(&Pred2) );
248 }
249
250 //! predicate 'or' composition predicate
251 /*!
252 Construct the \c class_or predicate. This predicate can be used
253 to logically combine two classification predicates. \c class_or holds,
254 if one of the predicates return true.
255
256 \param Pred1 The first predicate
257 \param Pred2 The second predicate
258 \return An instance of the \c class_or predicate
259 */
260 template<typename Pred1T, typename Pred2T>
261 inline detail::pred_orF<Pred1T, Pred2T>
262 operator||(
263 const predicate_facade<Pred1T>& Pred1,
264 const predicate_facade<Pred2T>& Pred2 )
265 {
266 // Doing the static_cast with the pointer instead of the reference
267 // is a workaround for some compilers which have problems with
268 // static_cast's of template references, i.e. CW8. /grafik/
269 return detail::pred_orF<Pred1T,Pred2T>(
270 *static_cast<const Pred1T*>(&Pred1),
271 *static_cast<const Pred2T*>(&Pred2));
272 }
273
274 //! predicate negation operator
275 /*!
276 Construct the \c class_not predicate. This predicate represents a negation.
277 \c class_or holds if of the predicates return false.
278
279 \param Pred The predicate to be negated
280 \return An instance of the \c class_not predicate
281 */
282 template<typename PredT>
283 inline detail::pred_notF<PredT>
284 operator!( const predicate_facade<PredT>& Pred )
285 {
286 // Doing the static_cast with the pointer instead of the reference
287 // is a workaround for some compilers which have problems with
288 // static_cast's of template references, i.e. CW8. /grafik/
289 return detail::pred_notF<PredT>(*static_cast<const PredT*>(&Pred));
290 }
291
292 } // namespace algorithm
293
294 // pull names to the boost namespace
295 using algorithm::is_classified;
296 using algorithm::is_space;
297 using algorithm::is_alnum;
298 using algorithm::is_alpha;
299 using algorithm::is_cntrl;
300 using algorithm::is_digit;
301 using algorithm::is_graph;
302 using algorithm::is_lower;
303 using algorithm::is_upper;
304 using algorithm::is_print;
305 using algorithm::is_punct;
306 using algorithm::is_xdigit;
307 using algorithm::is_any_of;
308 using algorithm::is_from_range;
309
310} // namespace boost
311
312#endif // BOOST_STRING_PREDICATE_HPP

/usr/include/boost/algorithm/string/detail/classification.hpp

1// Boost string_algo library classification.hpp header file ---------------------------//
2
3// Copyright Pavol Droba 2002-2003.
4//
5// Distributed under the Boost Software License, Version 1.0.
6// (See accompanying file LICENSE_1_0.txt or copy at
7// http://www.boost.org/LICENSE_1_0.txt)
8
9// See http://www.boost.org/ for updates, documentation, and revision history.
10
11#ifndef BOOST_STRING_CLASSIFICATION_DETAIL_HPP
12#define BOOST_STRING_CLASSIFICATION_DETAIL_HPP
13
14#include <boost/algorithm/string/config.hpp>
15#include <algorithm>
16#include <cstring>
17#include <functional>
18#include <locale>
19
20#include <boost/range/begin.hpp>
21#include <boost/range/distance.hpp>
22#include <boost/range/end.hpp>
23
24#include <boost/algorithm/string/predicate_facade.hpp>
25#include <boost/type_traits/remove_const.hpp>
26
27namespace boost {
28 namespace algorithm {
29 namespace detail {
30
31// classification functors -----------------------------------------------//
32
33 // is_classified functor
34 struct is_classifiedF :
35 public predicate_facade<is_classifiedF>
36 {
37 // Boost.ResultOf support
38 typedef bool result_type;
39
40 // Constructor from a locale
41 is_classifiedF(std::ctype_base::mask Type, std::locale const & Loc = std::locale()) :
42 m_Type(Type), m_Locale(Loc) {}
43 // Operation
44 template<typename CharT>
45 bool operator()( CharT Ch ) const
46 {
47 return std::use_facet< std::ctype<CharT> >(m_Locale).is( m_Type, Ch );
48 }
49
50 #if defined(BOOST_BORLANDC) && (BOOST_BORLANDC >= 0x560) && (BOOST_BORLANDC <= 0x582) && !defined(_USE_OLD_RW_STL)
51 template<>
52 bool operator()( char const Ch ) const
53 {
54 return std::use_facet< std::ctype<char> >(m_Locale).is( m_Type, Ch );
55 }
56 #endif
57
58 private:
59 std::ctype_base::mask m_Type;
60 std::locale m_Locale;
61 };
62
63
64 // is_any_of functor
65 /*
66 returns true if the value is from the specified set
67 */
68 template<typename CharT>
69 struct is_any_ofF :
70 public predicate_facade<is_any_ofF<CharT> >
71 {
72 private:
73 // set cannot operate on const value-type
74 typedef typename ::boost::remove_const<CharT>::type set_value_type;
75
76 public:
77 // Boost.ResultOf support
78 typedef bool result_type;
79
80 // Constructor
81 template<typename RangeT>
82 is_any_ofF( const RangeT& Range ) : m_Size(0)
83 {
84 // Prepare storage
85 m_Storage.m_dynSet=0;
86
87 std::size_t Size=::boost::distance(Range);
88 m_Size=Size;
89 set_value_type* Storage=0;
90
91 if(use_fixed_storage(m_Size))
6
Taking false branch
92 {
93 // Use fixed storage
94 Storage=&m_Storage.m_fixSet[0];
95 }
96 else
97 {
98 // Use dynamic storage
99 m_Storage.m_dynSet=new set_value_type[m_Size];
7
Memory is allocated
100 Storage=m_Storage.m_dynSet;
101 }
102
103 // Use fixed storage
104 ::std::copy(::boost::begin(Range), ::boost::end(Range), Storage);
105 ::std::sort(Storage, Storage+m_Size);
106 }
107
108 // Copy constructor
109 is_any_ofF(const is_any_ofF& Other) : m_Size(Other.m_Size)
110 {
111 // Prepare storage
112 m_Storage.m_dynSet=0;
113 const set_value_type* SrcStorage=0;
114 set_value_type* DestStorage=0;
115
116 if(use_fixed_storage(m_Size))
117 {
118 // Use fixed storage
119 DestStorage=&m_Storage.m_fixSet[0];
120 SrcStorage=&Other.m_Storage.m_fixSet[0];
121 }
122 else
123 {
124 // Use dynamic storage
125 m_Storage.m_dynSet=new set_value_type[m_Size];
126 DestStorage=m_Storage.m_dynSet;
127 SrcStorage=Other.m_Storage.m_dynSet;
128 }
129
130 // Use fixed storage
131 ::std::memcpy(DestStorage, SrcStorage, sizeof(set_value_type)*m_Size);
132 }
133
134 // Destructor
135 ~is_any_ofF()
136 {
137 if(!use_fixed_storage(m_Size) && m_Storage.m_dynSet!=0)
138 {
139 delete [] m_Storage.m_dynSet;
140 }
141 }
142
143 // Assignment
144 is_any_ofF& operator=(const is_any_ofF& Other)
145 {
146 // Handle self assignment
147 if(this==&Other) return *this;
148
149 // Prepare storage
150 const set_value_type* SrcStorage;
151 set_value_type* DestStorage;
152
153 if(use_fixed_storage(Other.m_Size))
154 {
155 // Use fixed storage
156 DestStorage=&m_Storage.m_fixSet[0];
157 SrcStorage=&Other.m_Storage.m_fixSet[0];
158
159 // Delete old storage if was present
160 if(!use_fixed_storage(m_Size) && m_Storage.m_dynSet!=0)
161 {
162 delete [] m_Storage.m_dynSet;
163 }
164
165 // Set new size
166 m_Size=Other.m_Size;
167 }
168 else
169 {
170 // Other uses dynamic storage
171 SrcStorage=Other.m_Storage.m_dynSet;
172
173 // Check what kind of storage are we using right now
174 if(use_fixed_storage(m_Size))
175 {
176 // Using fixed storage, allocate new
177 set_value_type* pTemp=new set_value_type[Other.m_Size];
178 DestStorage=pTemp;
179 m_Storage.m_dynSet=pTemp;
180 m_Size=Other.m_Size;
181 }
182 else
183 {
184 // Using dynamic storage, check if can reuse
185 if(m_Storage.m_dynSet!=0 && m_Size>=Other.m_Size && m_Size<Other.m_Size*2)
186 {
187 // Reuse the current storage
188 DestStorage=m_Storage.m_dynSet;
189 m_Size=Other.m_Size;
190 }
191 else
192 {
193 // Allocate the new one
194 set_value_type* pTemp=new set_value_type[Other.m_Size];
195 DestStorage=pTemp;
196
197 // Delete old storage if necessary
198 if(m_Storage.m_dynSet!=0)
199 {
200 delete [] m_Storage.m_dynSet;
201 }
202 // Store the new storage
203 m_Storage.m_dynSet=pTemp;
204 // Set new size
205 m_Size=Other.m_Size;
206 }
207 }
208 }
209
210 // Copy the data
211 ::std::memcpy(DestStorage, SrcStorage, sizeof(set_value_type)*m_Size);
212
213 return *this;
214 }
215
216 // Operation
217 template<typename Char2T>
218 bool operator()( Char2T Ch ) const
219 {
220 const set_value_type* Storage=
221 (use_fixed_storage(m_Size))
222 ? &m_Storage.m_fixSet[0]
223 : m_Storage.m_dynSet;
224
225 return ::std::binary_search(Storage, Storage+m_Size, Ch);
226 }
227 private:
228 // check if the size is eligible for fixed storage
229 static bool use_fixed_storage(std::size_t size)
230 {
231 return size<=sizeof(set_value_type*)*2;
232 }
233
234
235 private:
236 // storage
237 // The actual used storage is selected on the type
238 union
239 {
240 set_value_type* m_dynSet;
241 set_value_type m_fixSet[sizeof(set_value_type*)*2];
242 }
243 m_Storage;
244
245 // storage size
246 ::std::size_t m_Size;
247 };
248
249 // is_from_range functor
250 /*
251 returns true if the value is from the specified range.
252 (i.e. x>=From && x>=To)
253 */
254 template<typename CharT>
255 struct is_from_rangeF :
256 public predicate_facade< is_from_rangeF<CharT> >
257 {
258 // Boost.ResultOf support
259 typedef bool result_type;
260
261 // Constructor
262 is_from_rangeF( CharT From, CharT To ) : m_From(From), m_To(To) {}
263
264 // Operation
265 template<typename Char2T>
266 bool operator()( Char2T Ch ) const
267 {
268 return ( m_From <= Ch ) && ( Ch <= m_To );
269 }
270
271 private:
272 CharT m_From;
273 CharT m_To;
274 };
275
276 // class_and composition predicate
277 template<typename Pred1T, typename Pred2T>
278 struct pred_andF :
279 public predicate_facade< pred_andF<Pred1T,Pred2T> >
280 {
281 public:
282
283 // Boost.ResultOf support
284 typedef bool result_type;
285
286 // Constructor
287 pred_andF( Pred1T Pred1, Pred2T Pred2 ) :
288 m_Pred1(Pred1), m_Pred2(Pred2) {}
289
290 // Operation
291 template<typename CharT>
292 bool operator()( CharT Ch ) const
293 {
294 return m_Pred1(Ch) && m_Pred2(Ch);
295 }
296
297 private:
298 Pred1T m_Pred1;
299 Pred2T m_Pred2;
300 };
301
302 // class_or composition predicate
303 template<typename Pred1T, typename Pred2T>
304 struct pred_orF :
305 public predicate_facade< pred_orF<Pred1T,Pred2T> >
306 {
307 public:
308 // Boost.ResultOf support
309 typedef bool result_type;
310
311 // Constructor
312 pred_orF( Pred1T Pred1, Pred2T Pred2 ) :
313 m_Pred1(Pred1), m_Pred2(Pred2) {}
314
315 // Operation
316 template<typename CharT>
317 bool operator()( CharT Ch ) const
318 {
319 return m_Pred1(Ch) || m_Pred2(Ch);
320 }
321
322 private:
323 Pred1T m_Pred1;
324 Pred2T m_Pred2;
325 };
326
327 // class_not composition predicate
328 template< typename PredT >
329 struct pred_notF :
330 public predicate_facade< pred_notF<PredT> >
331 {
332 public:
333 // Boost.ResultOf support
334 typedef bool result_type;
335
336 // Constructor
337 pred_notF( PredT Pred ) : m_Pred(Pred) {}
338
339 // Operation
340 template<typename CharT>
341 bool operator()( CharT Ch ) const
342 {
343 return !m_Pred(Ch);
344 }
345
346 private:
347 PredT m_Pred;
348 };
349
350 } // namespace detail
351 } // namespace algorithm
352} // namespace boost
353
354
355#endif // BOOST_STRING_CLASSIFICATION_DETAIL_HPP

/usr/bin/../lib/gcc/x86_64-redhat-linux/13/../../../../include/c++/13/bits/basic_string.h

1// Components for manipulating sequences of characters -*- C++ -*-
2
3// Copyright (C) 1997-2023 Free Software Foundation, Inc.
4//
5// This file is part of the GNU ISO C++ Library. This library is free
6// software; you can redistribute it and/or modify it under the
7// terms of the GNU General Public License as published by the
8// Free Software Foundation; either version 3, or (at your option)
9// any later version.
10
11// This library is distributed in the hope that it will be useful,
12// but WITHOUT ANY WARRANTY; without even the implied warranty of
13// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14// GNU General Public License for more details.
15
16// Under Section 7 of GPL version 3, you are granted additional
17// permissions described in the GCC Runtime Library Exception, version
18// 3.1, as published by the Free Software Foundation.
19
20// You should have received a copy of the GNU General Public License and
21// a copy of the GCC Runtime Library Exception along with this program;
22// see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
23// <http://www.gnu.org/licenses/>.
24
25/** @file bits/basic_string.h
26 * This is an internal header file, included by other library headers.
27 * Do not attempt to use it directly. @headername{string}
28 */
29
30//
31// ISO C++ 14882: 21 Strings library
32//
33
34#ifndef _BASIC_STRING_H1
35#define _BASIC_STRING_H1 1
36
37#pragma GCC system_header
38
39#include <ext/alloc_traits.h>
40#include <debug/debug.h>
41
42#if __cplusplus202002L >= 201103L
43#include <initializer_list>
44#endif
45
46#if __cplusplus202002L >= 201703L
47# include <string_view>
48#endif
49
50#if ! _GLIBCXX_USE_CXX11_ABI1
51# include "cow_string.h"
52#else
53namespace std _GLIBCXX_VISIBILITY(default)__attribute__ ((__visibility__ ("default")))
54{
55_GLIBCXX_BEGIN_NAMESPACE_VERSION
56_GLIBCXX_BEGIN_NAMESPACE_CXX11namespace __cxx11 {
57
58#ifdef __cpp_lib_is_constant_evaluated201811L
59// Support P0980R1 in C++20.
60# define __cpp_lib_constexpr_string201907L 201907L
61#elif __cplusplus202002L >= 201703L && _GLIBCXX_HAVE_IS_CONSTANT_EVALUATED1
62// Support P0426R1 changes to char_traits in C++17.
63# define __cpp_lib_constexpr_string201907L 201611L
64#endif
65
66 /**
67 * @class basic_string basic_string.h <string>
68 * @brief Managing sequences of characters and character-like objects.
69 *
70 * @ingroup strings
71 * @ingroup sequences
72 * @headerfile string
73 * @since C++98
74 *
75 * @tparam _CharT Type of character
76 * @tparam _Traits Traits for character type, defaults to
77 * char_traits<_CharT>.
78 * @tparam _Alloc Allocator type, defaults to allocator<_CharT>.
79 *
80 * Meets the requirements of a <a href="tables.html#65">container</a>, a
81 * <a href="tables.html#66">reversible container</a>, and a
82 * <a href="tables.html#67">sequence</a>. Of the
83 * <a href="tables.html#68">optional sequence requirements</a>, only
84 * @c push_back, @c at, and @c %array access are supported.
85 */
86 template<typename _CharT, typename _Traits, typename _Alloc>
87 class basic_string
88 {
89 typedef typename __gnu_cxx::__alloc_traits<_Alloc>::template
90 rebind<_CharT>::other _Char_alloc_type;
91
92 typedef __gnu_cxx::__alloc_traits<_Char_alloc_type> _Alloc_traits;
93
94 // Types:
95 public:
96 typedef _Traits traits_type;
97 typedef typename _Traits::char_type value_type;
98 typedef _Char_alloc_type allocator_type;
99 typedef typename _Alloc_traits::size_type size_type;
100 typedef typename _Alloc_traits::difference_type difference_type;
101 typedef typename _Alloc_traits::reference reference;
102 typedef typename _Alloc_traits::const_reference const_reference;
103 typedef typename _Alloc_traits::pointer pointer;
104 typedef typename _Alloc_traits::const_pointer const_pointer;
105 typedef __gnu_cxx::__normal_iterator<pointer, basic_string> iterator;
106 typedef __gnu_cxx::__normal_iterator<const_pointer, basic_string>
107 const_iterator;
108 typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
109 typedef std::reverse_iterator<iterator> reverse_iterator;
110
111 /// Value returned by various member functions when they fail.
112 static const size_type npos = static_cast<size_type>(-1);
113
114 protected:
115 // type used for positions in insert, erase etc.
116#if __cplusplus202002L < 201103L
117 typedef iterator __const_iterator;
118#else
119 typedef const_iterator __const_iterator;
120#endif
121
122 private:
123 static _GLIBCXX20_CONSTEXPRconstexpr pointer
124 _S_allocate(_Char_alloc_type& __a, size_type __n)
125 {
126 pointer __p = _Alloc_traits::allocate(__a, __n);
127#if __cpp_lib_constexpr_string201907L >= 201907L
128 // std::char_traits begins the lifetime of characters,
129 // but custom traits might not, so do it here.
130 if constexpr (!is_same_v<_Traits, char_traits<_CharT>>)
131 if (std::__is_constant_evaluated())
132 // Begin the lifetime of characters in allocated storage.
133 for (size_type __i = 0; __i < __n; ++__i)
134 std::construct_at(__builtin_addressof(__p[__i]));
135#endif
136 return __p;
137 }
138
139#if __cplusplus202002L >= 201703L
140 // A helper type for avoiding boiler-plate.
141 typedef basic_string_view<_CharT, _Traits> __sv_type;
142
143 template<typename _Tp, typename _Res>
144 using _If_sv = enable_if_t<
145 __and_<is_convertible<const _Tp&, __sv_type>,
146 __not_<is_convertible<const _Tp*, const basic_string*>>,
147 __not_<is_convertible<const _Tp&, const _CharT*>>>::value,
148 _Res>;
149
150 // Allows an implicit conversion to __sv_type.
151 _GLIBCXX20_CONSTEXPRconstexpr
152 static __sv_type
153 _S_to_string_view(__sv_type __svt) noexcept
154 { return __svt; }
155
156 // Wraps a string_view by explicit conversion and thus
157 // allows to add an internal constructor that does not
158 // participate in overload resolution when a string_view
159 // is provided.
160 struct __sv_wrapper
161 {
162 _GLIBCXX20_CONSTEXPRconstexpr explicit
163 __sv_wrapper(__sv_type __sv) noexcept : _M_sv(__sv) { }
164
165 __sv_type _M_sv;
166 };
167
168 /**
169 * @brief Only internally used: Construct string from a string view
170 * wrapper.
171 * @param __svw string view wrapper.
172 * @param __a Allocator to use.
173 */
174 _GLIBCXX20_CONSTEXPRconstexpr
175 explicit
176 basic_string(__sv_wrapper __svw, const _Alloc& __a)
177 : basic_string(__svw._M_sv.data(), __svw._M_sv.size(), __a) { }
178#endif
179
180 // Use empty-base optimization: http://www.cantrip.org/emptyopt.html
181 struct _Alloc_hider : allocator_type // TODO check __is_final
182 {
183#if __cplusplus202002L < 201103L
184 _Alloc_hider(pointer __dat, const _Alloc& __a = _Alloc())
185 : allocator_type(__a), _M_p(__dat) { }
186#else
187 _GLIBCXX20_CONSTEXPRconstexpr
188 _Alloc_hider(pointer __dat, const _Alloc& __a)
189 : allocator_type(__a), _M_p(__dat) { }
190
191 _GLIBCXX20_CONSTEXPRconstexpr
192 _Alloc_hider(pointer __dat, _Alloc&& __a = _Alloc())
193 : allocator_type(std::move(__a)), _M_p(__dat) { }
194#endif
195
196 pointer _M_p; // The actual data.
197 };
198
199 _Alloc_hider _M_dataplus;
200 size_type _M_string_length;
201
202 enum { _S_local_capacity = 15 / sizeof(_CharT) };
203
204 union
205 {
206 _CharT _M_local_buf[_S_local_capacity + 1];
207 size_type _M_allocated_capacity;
208 };
209
210 _GLIBCXX20_CONSTEXPRconstexpr
211 void
212 _M_data(pointer __p)
213 { _M_dataplus._M_p = __p; }
214
215 _GLIBCXX20_CONSTEXPRconstexpr
216 void
217 _M_length(size_type __length)
218 { _M_string_length = __length; }
219
220 _GLIBCXX20_CONSTEXPRconstexpr
221 pointer
222 _M_data() const
223 { return _M_dataplus._M_p; }
224
225 _GLIBCXX20_CONSTEXPRconstexpr
226 pointer
227 _M_local_data()
228 {
229#if __cplusplus202002L >= 201103L
230 return std::pointer_traits<pointer>::pointer_to(*_M_local_buf);
231#else
232 return pointer(_M_local_buf);
233#endif
234 }
235
236 _GLIBCXX20_CONSTEXPRconstexpr
237 const_pointer
238 _M_local_data() const
239 {
240#if __cplusplus202002L >= 201103L
241 return std::pointer_traits<const_pointer>::pointer_to(*_M_local_buf);
242#else
243 return const_pointer(_M_local_buf);
244#endif
245 }
246
247 _GLIBCXX20_CONSTEXPRconstexpr
248 void
249 _M_capacity(size_type __capacity)
250 { _M_allocated_capacity = __capacity; }
251
252 _GLIBCXX20_CONSTEXPRconstexpr
253 void
254 _M_set_length(size_type __n)
255 {
256 _M_length(__n);
257 traits_type::assign(_M_data()[__n], _CharT());
258 }
259
260 _GLIBCXX20_CONSTEXPRconstexpr
261 bool
262 _M_is_local() const
263 {
264 if (_M_data() == _M_local_data())
265 {
266 if (_M_string_length > _S_local_capacity)
267 __builtin_unreachable();
268 return true;
269 }
270 return false;
271 }
272
273 // Create & Destroy
274 _GLIBCXX20_CONSTEXPRconstexpr
275 pointer
276 _M_create(size_type&, size_type);
277
278 _GLIBCXX20_CONSTEXPRconstexpr
279 void
280 _M_dispose()
281 {
282 if (!_M_is_local())
283 _M_destroy(_M_allocated_capacity);
284 }
285
286 _GLIBCXX20_CONSTEXPRconstexpr
287 void
288 _M_destroy(size_type __size) throw()
289 { _Alloc_traits::deallocate(_M_get_allocator(), _M_data(), __size + 1); }
290
291#if __cplusplus202002L < 201103L || defined _GLIBCXX_DEFINING_STRING_INSTANTIATIONS
292 // _M_construct_aux is used to implement the 21.3.1 para 15 which
293 // requires special behaviour if _InIterator is an integral type
294 template<typename _InIterator>
295 void
296 _M_construct_aux(_InIterator __beg, _InIterator __end,
297 std::__false_type)
298 {
299 typedef typename iterator_traits<_InIterator>::iterator_category _Tag;
300 _M_construct(__beg, __end, _Tag());
301 }
302
303 // _GLIBCXX_RESOLVE_LIB_DEFECTS
304 // 438. Ambiguity in the "do the right thing" clause
305 template<typename _Integer>
306 void
307 _M_construct_aux(_Integer __beg, _Integer __end, std::__true_type)
308 { _M_construct_aux_2(static_cast<size_type>(__beg), __end); }
309
310 void
311 _M_construct_aux_2(size_type __req, _CharT __c)
312 { _M_construct(__req, __c); }
313#endif
314
315 // For Input Iterators, used in istreambuf_iterators, etc.
316 template<typename _InIterator>
317 _GLIBCXX20_CONSTEXPRconstexpr
318 void
319 _M_construct(_InIterator __beg, _InIterator __end,
320 std::input_iterator_tag);
321
322 // For forward_iterators up to random_access_iterators, used for
323 // string::iterator, _CharT*, etc.
324 template<typename _FwdIterator>
325 _GLIBCXX20_CONSTEXPRconstexpr
326 void
327 _M_construct(_FwdIterator __beg, _FwdIterator __end,
328 std::forward_iterator_tag);
329
330 _GLIBCXX20_CONSTEXPRconstexpr
331 void
332 _M_construct(size_type __req, _CharT __c);
333
334 _GLIBCXX20_CONSTEXPRconstexpr
335 allocator_type&
336 _M_get_allocator()
337 { return _M_dataplus; }
338
339 _GLIBCXX20_CONSTEXPRconstexpr
340 const allocator_type&
341 _M_get_allocator() const
342 { return _M_dataplus; }
343
344 // Ensure that _M_local_buf is the active member of the union.
345 __attribute__((__always_inline__))
346 _GLIBCXX14_CONSTEXPRconstexpr
347 pointer
348 _M_use_local_data() _GLIBCXX_NOEXCEPTnoexcept
349 {
350#if __cpp_lib_is_constant_evaluated201811L
351 if (std::is_constant_evaluated())
352 for (size_type __i = 0; __i <= _S_local_capacity; ++__i)
353 _M_local_buf[__i] = _CharT();
354#endif
355 return _M_local_data();
356 }
357
358 private:
359
360#ifdef _GLIBCXX_DISAMBIGUATE_REPLACE_INST
361 // The explicit instantiations in misc-inst.cc require this due to
362 // https://gcc.gnu.org/bugzilla/show_bug.cgi?id=64063
363 template<typename _Tp, bool _Requires =
364 !__are_same<_Tp, _CharT*>::__value
365 && !__are_same<_Tp, const _CharT*>::__value
366 && !__are_same<_Tp, iterator>::__value
367 && !__are_same<_Tp, const_iterator>::__value>
368 struct __enable_if_not_native_iterator
369 { typedef basic_string& __type; };
370 template<typename _Tp>
371 struct __enable_if_not_native_iterator<_Tp, false> { };
372#endif
373
374 _GLIBCXX20_CONSTEXPRconstexpr
375 size_type
376 _M_check(size_type __pos, const char* __s) const
377 {
378 if (__pos > this->size())
379 __throw_out_of_range_fmt(__N("%s: __pos (which is %zu) > "("%s: __pos (which is %zu) > " "this->size() (which is %zu)"
)
380 "this->size() (which is %zu)")("%s: __pos (which is %zu) > " "this->size() (which is %zu)"
)
,
381 __s, __pos, this->size());
382 return __pos;
383 }
384
385 _GLIBCXX20_CONSTEXPRconstexpr
386 void
387 _M_check_length(size_type __n1, size_type __n2, const char* __s) const
388 {
389 if (this->max_size() - (this->size() - __n1) < __n2)
390 __throw_length_error(__N(__s)(__s));
391 }
392
393
394 // NB: _M_limit doesn't check for a bad __pos value.
395 _GLIBCXX20_CONSTEXPRconstexpr
396 size_type
397 _M_limit(size_type __pos, size_type __off) const _GLIBCXX_NOEXCEPTnoexcept
398 {
399 const bool __testoff = __off < this->size() - __pos;
400 return __testoff ? __off : this->size() - __pos;
401 }
402
403 // True if _Rep and source do not overlap.
404 bool
405 _M_disjunct(const _CharT* __s) const _GLIBCXX_NOEXCEPTnoexcept
406 {
407 return (less<const _CharT*>()(__s, _M_data())
408 || less<const _CharT*>()(_M_data() + this->size(), __s));
409 }
410
411 // When __n = 1 way faster than the general multichar
412 // traits_type::copy/move/assign.
413 _GLIBCXX20_CONSTEXPRconstexpr
414 static void
415 _S_copy(_CharT* __d, const _CharT* __s, size_type __n)
416 {
417 if (__n == 1)
418 traits_type::assign(*__d, *__s);
419 else
420 traits_type::copy(__d, __s, __n);
421 }
422
423 _GLIBCXX20_CONSTEXPRconstexpr
424 static void
425 _S_move(_CharT* __d, const _CharT* __s, size_type __n)
426 {
427 if (__n == 1)
428 traits_type::assign(*__d, *__s);
429 else
430 traits_type::move(__d, __s, __n);
431 }
432
433 _GLIBCXX20_CONSTEXPRconstexpr
434 static void
435 _S_assign(_CharT* __d, size_type __n, _CharT __c)
436 {
437 if (__n == 1)
438 traits_type::assign(*__d, __c);
439 else
440 traits_type::assign(__d, __n, __c);
441 }
442
443 // _S_copy_chars is a separate template to permit specialization
444 // to optimize for the common case of pointers as iterators.
445 template<class _Iterator>
446 _GLIBCXX20_CONSTEXPRconstexpr
447 static void
448 _S_copy_chars(_CharT* __p, _Iterator __k1, _Iterator __k2)
449 {
450 for (; __k1 != __k2; ++__k1, (void)++__p)
451 traits_type::assign(*__p, *__k1); // These types are off.
452 }
453
454 _GLIBCXX20_CONSTEXPRconstexpr
455 static void
456 _S_copy_chars(_CharT* __p, iterator __k1, iterator __k2) _GLIBCXX_NOEXCEPTnoexcept
457 { _S_copy_chars(__p, __k1.base(), __k2.base()); }
458
459 _GLIBCXX20_CONSTEXPRconstexpr
460 static void
461 _S_copy_chars(_CharT* __p, const_iterator __k1, const_iterator __k2)
462 _GLIBCXX_NOEXCEPTnoexcept
463 { _S_copy_chars(__p, __k1.base(), __k2.base()); }
464
465 _GLIBCXX20_CONSTEXPRconstexpr
466 static void
467 _S_copy_chars(_CharT* __p, _CharT* __k1, _CharT* __k2) _GLIBCXX_NOEXCEPTnoexcept
468 { _S_copy(__p, __k1, __k2 - __k1); }
469
470 _GLIBCXX20_CONSTEXPRconstexpr
471 static void
472 _S_copy_chars(_CharT* __p, const _CharT* __k1, const _CharT* __k2)
473 _GLIBCXX_NOEXCEPTnoexcept
474 { _S_copy(__p, __k1, __k2 - __k1); }
475
476 _GLIBCXX20_CONSTEXPRconstexpr
477 static int
478 _S_compare(size_type __n1, size_type __n2) _GLIBCXX_NOEXCEPTnoexcept
479 {
480 const difference_type __d = difference_type(__n1 - __n2);
481
482 if (__d > __gnu_cxx::__numeric_traits<int>::__max)
483 return __gnu_cxx::__numeric_traits<int>::__max;
484 else if (__d < __gnu_cxx::__numeric_traits<int>::__min)
485 return __gnu_cxx::__numeric_traits<int>::__min;
486 else
487 return int(__d);
488 }
489
490 _GLIBCXX20_CONSTEXPRconstexpr
491 void
492 _M_assign(const basic_string&);
493
494 _GLIBCXX20_CONSTEXPRconstexpr
495 void
496 _M_mutate(size_type __pos, size_type __len1, const _CharT* __s,
497 size_type __len2);
498
499 _GLIBCXX20_CONSTEXPRconstexpr
500 void
501 _M_erase(size_type __pos, size_type __n);
502
503 public:
504 // Construct/copy/destroy:
505 // NB: We overload ctors in some cases instead of using default
506 // arguments, per 17.4.4.4 para. 2 item 2.
507
508 /**
509 * @brief Default constructor creates an empty string.
510 */
511 _GLIBCXX20_CONSTEXPRconstexpr
512 basic_string()
513 _GLIBCXX_NOEXCEPT_IF(is_nothrow_default_constructible<_Alloc>::value)noexcept(is_nothrow_default_constructible<_Alloc>::value
)
514 : _M_dataplus(_M_local_data())
515 {
516 _M_use_local_data();
517 _M_set_length(0);
518 }
519
520 /**
521 * @brief Construct an empty string using allocator @a a.
522 */
523 _GLIBCXX20_CONSTEXPRconstexpr
524 explicit
525 basic_string(const _Alloc& __a) _GLIBCXX_NOEXCEPTnoexcept
526 : _M_dataplus(_M_local_data(), __a)
527 {
528 _M_use_local_data();
529 _M_set_length(0);
530 }
531
532 /**
533 * @brief Construct string with copy of value of @a __str.
534 * @param __str Source string.
535 */
536 _GLIBCXX20_CONSTEXPRconstexpr
537 basic_string(const basic_string& __str)
538 : _M_dataplus(_M_local_data(),
539 _Alloc_traits::_S_select_on_copy(__str._M_get_allocator()))
540 {
541 _M_construct(__str._M_data(), __str._M_data() + __str.length(),
542 std::forward_iterator_tag());
543 }
544
545 // _GLIBCXX_RESOLVE_LIB_DEFECTS
546 // 2583. no way to supply an allocator for basic_string(str, pos)
547 /**
548 * @brief Construct string as copy of a substring.
549 * @param __str Source string.
550 * @param __pos Index of first character to copy from.
551 * @param __a Allocator to use.
552 */
553 _GLIBCXX20_CONSTEXPRconstexpr
554 basic_string(const basic_string& __str, size_type __pos,
555 const _Alloc& __a = _Alloc())
556 : _M_dataplus(_M_local_data(), __a)
557 {
558 const _CharT* __start = __str._M_data()
559 + __str._M_check(__pos, "basic_string::basic_string");
560 _M_construct(__start, __start + __str._M_limit(__pos, npos),
561 std::forward_iterator_tag());
562 }
563
564 /**
565 * @brief Construct string as copy of a substring.
566 * @param __str Source string.
567 * @param __pos Index of first character to copy from.
568 * @param __n Number of characters to copy.
569 */
570 _GLIBCXX20_CONSTEXPRconstexpr
571 basic_string(const basic_string& __str, size_type __pos,
572 size_type __n)
573 : _M_dataplus(_M_local_data())
574 {
575 const _CharT* __start = __str._M_data()
576 + __str._M_check(__pos, "basic_string::basic_string");
577 _M_construct(__start, __start + __str._M_limit(__pos, __n),
578 std::forward_iterator_tag());
579 }
580
581 /**
582 * @brief Construct string as copy of a substring.
583 * @param __str Source string.
584 * @param __pos Index of first character to copy from.
585 * @param __n Number of characters to copy.
586 * @param __a Allocator to use.
587 */
588 _GLIBCXX20_CONSTEXPRconstexpr
589 basic_string(const basic_string& __str, size_type __pos,
590 size_type __n, const _Alloc& __a)
591 : _M_dataplus(_M_local_data(), __a)
592 {
593 const _CharT* __start
594 = __str._M_data() + __str._M_check(__pos, "string::string");
595 _M_construct(__start, __start + __str._M_limit(__pos, __n),
596 std::forward_iterator_tag());
597 }
598
599 /**
600 * @brief Construct string initialized by a character %array.
601 * @param __s Source character %array.
602 * @param __n Number of characters to copy.
603 * @param __a Allocator to use (default is default allocator).
604 *
605 * NB: @a __s must have at least @a __n characters, &apos;\\0&apos;
606 * has no special meaning.
607 */
608 _GLIBCXX20_CONSTEXPRconstexpr
609 basic_string(const _CharT* __s, size_type __n,
610 const _Alloc& __a = _Alloc())
611 : _M_dataplus(_M_local_data(), __a)
612 {
613 // NB: Not required, but considered best practice.
614 if (__s == 0 && __n > 0)
615 std::__throw_logic_error(__N("basic_string: "("basic_string: " "construction from null is not valid")
616 "construction from null is not valid")("basic_string: " "construction from null is not valid"));
617 _M_construct(__s, __s + __n, std::forward_iterator_tag());
618 }
619
620 /**
621 * @brief Construct string as copy of a C string.
622 * @param __s Source C string.
623 * @param __a Allocator to use (default is default allocator).
624 */
625#if __cpp_deduction_guides201703L && ! defined _GLIBCXX_DEFINING_STRING_INSTANTIATIONS
626 // _GLIBCXX_RESOLVE_LIB_DEFECTS
627 // 3076. basic_string CTAD ambiguity
628 template<typename = _RequireAllocator<_Alloc>>
629#endif
630 _GLIBCXX20_CONSTEXPRconstexpr
631 basic_string(const _CharT* __s, const _Alloc& __a = _Alloc())
632 : _M_dataplus(_M_local_data(), __a)
633 {
634 // NB: Not required, but considered best practice.
635 if (__s == 0)
636 std::__throw_logic_error(__N("basic_string: "("basic_string: " "construction from null is not valid")
637 "construction from null is not valid")("basic_string: " "construction from null is not valid"));
638 const _CharT* __end = __s + traits_type::length(__s);
639 _M_construct(__s, __end, forward_iterator_tag());
640 }
641
642 /**
643 * @brief Construct string as multiple characters.
644 * @param __n Number of characters.
645 * @param __c Character to use.
646 * @param __a Allocator to use (default is default allocator).
647 */
648#if __cpp_deduction_guides201703L && ! defined _GLIBCXX_DEFINING_STRING_INSTANTIATIONS
649 // _GLIBCXX_RESOLVE_LIB_DEFECTS
650 // 3076. basic_string CTAD ambiguity
651 template<typename = _RequireAllocator<_Alloc>>
652#endif
653 _GLIBCXX20_CONSTEXPRconstexpr
654 basic_string(size_type __n, _CharT __c, const _Alloc& __a = _Alloc())
655 : _M_dataplus(_M_local_data(), __a)
656 { _M_construct(__n, __c); }
657
658#if __cplusplus202002L >= 201103L
659 /**
660 * @brief Move construct string.
661 * @param __str Source string.
662 *
663 * The newly-created string contains the exact contents of @a __str.
664 * @a __str is a valid, but unspecified string.
665 */
666 _GLIBCXX20_CONSTEXPRconstexpr
667 basic_string(basic_string&& __str) noexcept
668 : _M_dataplus(_M_local_data(), std::move(__str._M_get_allocator()))
669 {
670 if (__str._M_is_local())
671 {
672 traits_type::copy(_M_local_buf, __str._M_local_buf,
673 __str.length() + 1);
674 }
675 else
676 {
677 _M_data(__str._M_data());
678 _M_capacity(__str._M_allocated_capacity);
679 }
680
681 // Must use _M_length() here not _M_set_length() because
682 // basic_stringbuf relies on writing into unallocated capacity so
683 // we mess up the contents if we put a '\0' in the string.
684 _M_length(__str.length());
685 __str._M_data(__str._M_local_data());
686 __str._M_set_length(0);
687 }
688
689 /**
690 * @brief Construct string from an initializer %list.
691 * @param __l std::initializer_list of characters.
692 * @param __a Allocator to use (default is default allocator).
693 */
694 _GLIBCXX20_CONSTEXPRconstexpr
695 basic_string(initializer_list<_CharT> __l, const _Alloc& __a = _Alloc())
696 : _M_dataplus(_M_local_data(), __a)
697 { _M_construct(__l.begin(), __l.end(), std::forward_iterator_tag()); }
698
699 _GLIBCXX20_CONSTEXPRconstexpr
700 basic_string(const basic_string& __str, const _Alloc& __a)
701 : _M_dataplus(_M_local_data(), __a)
702 { _M_construct(__str.begin(), __str.end(), std::forward_iterator_tag()); }
703
704 _GLIBCXX20_CONSTEXPRconstexpr
705 basic_string(basic_string&& __str, const _Alloc& __a)
706 noexcept(_Alloc_traits::_S_always_equal())
707 : _M_dataplus(_M_local_data(), __a)
708 {
709 if (__str._M_is_local())
710 {
711 traits_type::copy(_M_local_buf, __str._M_local_buf,
712 __str.length() + 1);
713 _M_length(__str.length());
714 __str._M_set_length(0);
715 }
716 else if (_Alloc_traits::_S_always_equal()
717 || __str.get_allocator() == __a)
718 {
719 _M_data(__str._M_data());
720 _M_length(__str.length());
721 _M_capacity(__str._M_allocated_capacity);
722 __str._M_data(__str._M_local_buf);
723 __str._M_set_length(0);
724 }
725 else
726 _M_construct(__str.begin(), __str.end(), std::forward_iterator_tag());
727 }
728#endif // C++11
729
730#if __cplusplus202002L >= 202100L
731 basic_string(nullptr_t) = delete;
732 basic_string& operator=(nullptr_t) = delete;
733#endif // C++23
734
735 /**
736 * @brief Construct string as copy of a range.
737 * @param __beg Start of range.
738 * @param __end End of range.
739 * @param __a Allocator to use (default is default allocator).
740 */
741#if __cplusplus202002L >= 201103L
742 template<typename _InputIterator,
743 typename = std::_RequireInputIter<_InputIterator>>
744#else
745 template<typename _InputIterator>
746#endif
747 _GLIBCXX20_CONSTEXPRconstexpr
748 basic_string(_InputIterator __beg, _InputIterator __end,
749 const _Alloc& __a = _Alloc())
750 : _M_dataplus(_M_local_data(), __a), _M_string_length(0)
751 {
752#if __cplusplus202002L >= 201103L
753 _M_construct(__beg, __end, std::__iterator_category(__beg));
754#else
755 typedef typename std::__is_integer<_InputIterator>::__type _Integral;
756 _M_construct_aux(__beg, __end, _Integral());
757#endif
758 }
759
760#if __cplusplus202002L >= 201703L
761 /**
762 * @brief Construct string from a substring of a string_view.
763 * @param __t Source object convertible to string view.
764 * @param __pos The index of the first character to copy from __t.
765 * @param __n The number of characters to copy from __t.
766 * @param __a Allocator to use.
767 */
768 template<typename _Tp,
769 typename = enable_if_t<is_convertible_v<const _Tp&, __sv_type>>>
770 _GLIBCXX20_CONSTEXPRconstexpr
771 basic_string(const _Tp& __t, size_type __pos, size_type __n,
772 const _Alloc& __a = _Alloc())
773 : basic_string(_S_to_string_view(__t).substr(__pos, __n), __a) { }
774
775 /**
776 * @brief Construct string from a string_view.
777 * @param __t Source object convertible to string view.
778 * @param __a Allocator to use (default is default allocator).
779 */
780 template<typename _Tp, typename = _If_sv<_Tp, void>>
781 _GLIBCXX20_CONSTEXPRconstexpr
782 explicit
783 basic_string(const _Tp& __t, const _Alloc& __a = _Alloc())
784 : basic_string(__sv_wrapper(_S_to_string_view(__t)), __a) { }
785#endif // C++17
786
787 /**
788 * @brief Destroy the string instance.
789 */
790 _GLIBCXX20_CONSTEXPRconstexpr
791 ~basic_string()
792 { _M_dispose(); }
793
794 /**
795 * @brief Assign the value of @a str to this string.
796 * @param __str Source string.
797 */
798 _GLIBCXX20_CONSTEXPRconstexpr
799 basic_string&
800 operator=(const basic_string& __str)
801 {
802 return this->assign(__str);
803 }
804
805 /**
806 * @brief Copy contents of @a s into this string.
807 * @param __s Source null-terminated string.
808 */
809 _GLIBCXX20_CONSTEXPRconstexpr
810 basic_string&
811 operator=(const _CharT* __s)
812 { return this->assign(__s); }
813
814 /**
815 * @brief Set value to string of length 1.
816 * @param __c Source character.
817 *
818 * Assigning to a character makes this string length 1 and
819 * (*this)[0] == @a c.
820 */
821 _GLIBCXX20_CONSTEXPRconstexpr
822 basic_string&
823 operator=(_CharT __c)
824 {
825 this->assign(1, __c);
826 return *this;
827 }
828
829#if __cplusplus202002L >= 201103L
830 /**
831 * @brief Move assign the value of @a str to this string.
832 * @param __str Source string.
833 *
834 * The contents of @a str are moved into this string (without copying).
835 * @a str is a valid, but unspecified string.
836 */
837 // _GLIBCXX_RESOLVE_LIB_DEFECTS
838 // 2063. Contradictory requirements for string move assignment
839 _GLIBCXX20_CONSTEXPRconstexpr
840 basic_string&
841 operator=(basic_string&& __str)
842 noexcept(_Alloc_traits::_S_nothrow_move())
843 {
844 const bool __equal_allocs = _Alloc_traits::_S_always_equal()
845 || _M_get_allocator() == __str._M_get_allocator();
846 if (!_M_is_local() && _Alloc_traits::_S_propagate_on_move_assign()
847 && !__equal_allocs)
848 {
849 // Destroy existing storage before replacing allocator.
850 _M_destroy(_M_allocated_capacity);
851 _M_data(_M_local_data());
852 _M_set_length(0);
853 }
854 // Replace allocator if POCMA is true.
855 std::__alloc_on_move(_M_get_allocator(), __str._M_get_allocator());
856
857 if (__str._M_is_local())
858 {
859 // We've always got room for a short string, just copy it
860 // (unless this is a self-move, because that would violate the
861 // char_traits::copy precondition that the ranges don't overlap).
862 if (__builtin_expect(std::__addressof(__str) != this, true))
863 {
864 if (__str.size())
865 this->_S_copy(_M_data(), __str._M_data(), __str.size());
866 _M_set_length(__str.size());
867 }
868 }
869 else if (_Alloc_traits::_S_propagate_on_move_assign() || __equal_allocs)
870 {
871 // Just move the allocated pointer, our allocator can free it.
872 pointer __data = nullptr;
873 size_type __capacity;
874 if (!_M_is_local())
875 {
876 if (__equal_allocs)
877 {
878 // __str can reuse our existing storage.
879 __data = _M_data();
880 __capacity = _M_allocated_capacity;
881 }
882 else // __str can't use it, so free it.
883 _M_destroy(_M_allocated_capacity);
884 }
885
886 _M_data(__str._M_data());
887 _M_length(__str.length());
888 _M_capacity(__str._M_allocated_capacity);
889 if (__data)
890 {
891 __str._M_data(__data);
892 __str._M_capacity(__capacity);
893 }
894 else
895 __str._M_data(__str._M_local_buf);
896 }
897 else // Need to do a deep copy
898 assign(__str);
899 __str.clear();
900 return *this;
901 }
902
903 /**
904 * @brief Set value to string constructed from initializer %list.
905 * @param __l std::initializer_list.
906 */
907 _GLIBCXX20_CONSTEXPRconstexpr
908 basic_string&
909 operator=(initializer_list<_CharT> __l)
910 {
911 this->assign(__l.begin(), __l.size());
912 return *this;
913 }
914#endif // C++11
915
916#if __cplusplus202002L >= 201703L
917 /**
918 * @brief Set value to string constructed from a string_view.
919 * @param __svt An object convertible to string_view.
920 */
921 template<typename _Tp>
922 _GLIBCXX20_CONSTEXPRconstexpr
923 _If_sv<_Tp, basic_string&>
924 operator=(const _Tp& __svt)
925 { return this->assign(__svt); }
926
927 /**
928 * @brief Convert to a string_view.
929 * @return A string_view.
930 */
931 _GLIBCXX20_CONSTEXPRconstexpr
932 operator __sv_type() const noexcept
933 { return __sv_type(data(), size()); }
934#endif // C++17
935
936 // Iterators:
937 /**
938 * Returns a read/write iterator that points to the first character in
939 * the %string.
940 */
941 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
942 iterator
943 begin() _GLIBCXX_NOEXCEPTnoexcept
944 { return iterator(_M_data()); }
945
946 /**
947 * Returns a read-only (constant) iterator that points to the first
948 * character in the %string.
949 */
950 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
951 const_iterator
952 begin() const _GLIBCXX_NOEXCEPTnoexcept
953 { return const_iterator(_M_data()); }
954
955 /**
956 * Returns a read/write iterator that points one past the last
957 * character in the %string.
958 */
959 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
960 iterator
961 end() _GLIBCXX_NOEXCEPTnoexcept
962 { return iterator(_M_data() + this->size()); }
963
964 /**
965 * Returns a read-only (constant) iterator that points one past the
966 * last character in the %string.
967 */
968 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
969 const_iterator
970 end() const _GLIBCXX_NOEXCEPTnoexcept
971 { return const_iterator(_M_data() + this->size()); }
972
973 /**
974 * Returns a read/write reverse iterator that points to the last
975 * character in the %string. Iteration is done in reverse element
976 * order.
977 */
978 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
979 reverse_iterator
980 rbegin() _GLIBCXX_NOEXCEPTnoexcept
981 { return reverse_iterator(this->end()); }
982
983 /**
984 * Returns a read-only (constant) reverse iterator that points
985 * to the last character in the %string. Iteration is done in
986 * reverse element order.
987 */
988 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
989 const_reverse_iterator
990 rbegin() const _GLIBCXX_NOEXCEPTnoexcept
991 { return const_reverse_iterator(this->end()); }
992
993 /**
994 * Returns a read/write reverse iterator that points to one before the
995 * first character in the %string. Iteration is done in reverse
996 * element order.
997 */
998 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
999 reverse_iterator
1000 rend() _GLIBCXX_NOEXCEPTnoexcept
1001 { return reverse_iterator(this->begin()); }
1002
1003 /**
1004 * Returns a read-only (constant) reverse iterator that points
1005 * to one before the first character in the %string. Iteration
1006 * is done in reverse element order.
1007 */
1008 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1009 const_reverse_iterator
1010 rend() const _GLIBCXX_NOEXCEPTnoexcept
1011 { return const_reverse_iterator(this->begin()); }
1012
1013#if __cplusplus202002L >= 201103L
1014 /**
1015 * Returns a read-only (constant) iterator that points to the first
1016 * character in the %string.
1017 */
1018 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1019 const_iterator
1020 cbegin() const noexcept
1021 { return const_iterator(this->_M_data()); }
1022
1023 /**
1024 * Returns a read-only (constant) iterator that points one past the
1025 * last character in the %string.
1026 */
1027 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1028 const_iterator
1029 cend() const noexcept
1030 { return const_iterator(this->_M_data() + this->size()); }
1031
1032 /**
1033 * Returns a read-only (constant) reverse iterator that points
1034 * to the last character in the %string. Iteration is done in
1035 * reverse element order.
1036 */
1037 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1038 const_reverse_iterator
1039 crbegin() const noexcept
1040 { return const_reverse_iterator(this->end()); }
1041
1042 /**
1043 * Returns a read-only (constant) reverse iterator that points
1044 * to one before the first character in the %string. Iteration
1045 * is done in reverse element order.
1046 */
1047 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1048 const_reverse_iterator
1049 crend() const noexcept
1050 { return const_reverse_iterator(this->begin()); }
1051#endif
1052
1053 public:
1054 // Capacity:
1055 /// Returns the number of characters in the string, not including any
1056 /// null-termination.
1057 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1058 size_type
1059 size() const _GLIBCXX_NOEXCEPTnoexcept
1060 { return _M_string_length; }
1061
1062 /// Returns the number of characters in the string, not including any
1063 /// null-termination.
1064 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1065 size_type
1066 length() const _GLIBCXX_NOEXCEPTnoexcept
1067 { return _M_string_length; }
1068
1069 /// Returns the size() of the largest possible %string.
1070 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1071 size_type
1072 max_size() const _GLIBCXX_NOEXCEPTnoexcept
1073 { return (_Alloc_traits::max_size(_M_get_allocator()) - 1) / 2; }
1074
1075 /**
1076 * @brief Resizes the %string to the specified number of characters.
1077 * @param __n Number of characters the %string should contain.
1078 * @param __c Character to fill any new elements.
1079 *
1080 * This function will %resize the %string to the specified
1081 * number of characters. If the number is smaller than the
1082 * %string's current size the %string is truncated, otherwise
1083 * the %string is extended and new elements are %set to @a __c.
1084 */
1085 _GLIBCXX20_CONSTEXPRconstexpr
1086 void
1087 resize(size_type __n, _CharT __c);
1088
1089 /**
1090 * @brief Resizes the %string to the specified number of characters.
1091 * @param __n Number of characters the %string should contain.
1092 *
1093 * This function will resize the %string to the specified length. If
1094 * the new size is smaller than the %string's current size the %string
1095 * is truncated, otherwise the %string is extended and new characters
1096 * are default-constructed. For basic types such as char, this means
1097 * setting them to 0.
1098 */
1099 _GLIBCXX20_CONSTEXPRconstexpr
1100 void
1101 resize(size_type __n)
1102 { this->resize(__n, _CharT()); }
1103
1104#if __cplusplus202002L >= 201103L
1105#pragma GCC diagnostic push
1106#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
1107 /// A non-binding request to reduce capacity() to size().
1108 _GLIBCXX20_CONSTEXPRconstexpr
1109 void
1110 shrink_to_fit() noexcept
1111 { reserve(); }
1112#pragma GCC diagnostic pop
1113#endif
1114
1115#if __cplusplus202002L > 202002L
1116#define __cpp_lib_string_resize_and_overwrite 202110L
1117 /** Resize the string and call a function to fill it.
1118 *
1119 * @param __n The maximum size requested.
1120 * @param __op A callable object that writes characters to the string.
1121 *
1122 * This is a low-level function that is easy to misuse, be careful.
1123 *
1124 * Calling `str.resize_and_overwrite(n, op)` will reserve at least `n`
1125 * characters in `str`, evaluate `n2 = std::move(op)(str.data(), n)`,
1126 * and finally set the string length to `n2` (adding a null terminator
1127 * at the end). The function object `op` is allowed to write to the
1128 * extra capacity added by the initial reserve operation, which is not
1129 * allowed if you just call `str.reserve(n)` yourself.
1130 *
1131 * This can be used to efficiently fill a `string` buffer without the
1132 * overhead of zero-initializing characters that will be overwritten
1133 * anyway.
1134 *
1135 * The callable `op` must not access the string directly (only through
1136 * the pointer passed as its first argument), must not write more than
1137 * `n` characters to the string, must return a value no greater than `n`,
1138 * and must ensure that all characters up to the returned length are
1139 * valid after it returns (i.e. there must be no uninitialized values
1140 * left in the string after the call, because accessing them would
1141 * have undefined behaviour). If `op` exits by throwing an exception
1142 * the behaviour is undefined.
1143 *
1144 * @since C++23
1145 */
1146 template<typename _Operation>
1147 constexpr void
1148 resize_and_overwrite(size_type __n, _Operation __op);
1149#endif
1150
1151 /**
1152 * Returns the total number of characters that the %string can hold
1153 * before needing to allocate more memory.
1154 */
1155 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1156 size_type
1157 capacity() const _GLIBCXX_NOEXCEPTnoexcept
1158 {
1159 return _M_is_local() ? size_type(_S_local_capacity)
1160 : _M_allocated_capacity;
1161 }
1162
1163 /**
1164 * @brief Attempt to preallocate enough memory for specified number of
1165 * characters.
1166 * @param __res_arg Number of characters required.
1167 * @throw std::length_error If @a __res_arg exceeds @c max_size().
1168 *
1169 * This function attempts to reserve enough memory for the
1170 * %string to hold the specified number of characters. If the
1171 * number requested is more than max_size(), length_error is
1172 * thrown.
1173 *
1174 * The advantage of this function is that if optimal code is a
1175 * necessity and the user can determine the string length that will be
1176 * required, the user can reserve the memory in %advance, and thus
1177 * prevent a possible reallocation of memory and copying of %string
1178 * data.
1179 */
1180 _GLIBCXX20_CONSTEXPRconstexpr
1181 void
1182 reserve(size_type __res_arg);
1183
1184 /**
1185 * Equivalent to shrink_to_fit().
1186 */
1187#if __cplusplus202002L > 201703L
1188 [[deprecated("use shrink_to_fit() instead")]]
1189#endif
1190 _GLIBCXX20_CONSTEXPRconstexpr
1191 void
1192 reserve();
1193
1194 /**
1195 * Erases the string, making it empty.
1196 */
1197 _GLIBCXX20_CONSTEXPRconstexpr
1198 void
1199 clear() _GLIBCXX_NOEXCEPTnoexcept
1200 { _M_set_length(0); }
1201
1202 /**
1203 * Returns true if the %string is empty. Equivalent to
1204 * <code>*this == ""</code>.
1205 */
1206 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1207 bool
1208 empty() const _GLIBCXX_NOEXCEPTnoexcept
1209 { return this->size() == 0; }
1210
1211 // Element access:
1212 /**
1213 * @brief Subscript access to the data contained in the %string.
1214 * @param __pos The index of the character to access.
1215 * @return Read-only (constant) reference to the character.
1216 *
1217 * This operator allows for easy, array-style, data access.
1218 * Note that data access with this operator is unchecked and
1219 * out_of_range lookups are not defined. (For checked lookups
1220 * see at().)
1221 */
1222 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1223 const_reference
1224 operator[] (size_type __pos) const _GLIBCXX_NOEXCEPTnoexcept
1225 {
1226 __glibcxx_assert(__pos <= size())do { if (std::__is_constant_evaluated() && !bool(__pos
<= size())) __builtin_unreachable(); } while (false)
;
1227 return _M_data()[__pos];
1228 }
1229
1230 /**
1231 * @brief Subscript access to the data contained in the %string.
1232 * @param __pos The index of the character to access.
1233 * @return Read/write reference to the character.
1234 *
1235 * This operator allows for easy, array-style, data access.
1236 * Note that data access with this operator is unchecked and
1237 * out_of_range lookups are not defined. (For checked lookups
1238 * see at().)
1239 */
1240 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1241 reference
1242 operator[](size_type __pos)
1243 {
1244 // Allow pos == size() both in C++98 mode, as v3 extension,
1245 // and in C++11 mode.
1246 __glibcxx_assert(__pos <= size())do { if (std::__is_constant_evaluated() && !bool(__pos
<= size())) __builtin_unreachable(); } while (false)
;
1247 // In pedantic mode be strict in C++98 mode.
1248 _GLIBCXX_DEBUG_PEDASSERT(__cplusplus >= 201103L || __pos < size());
1249 return _M_data()[__pos];
1250 }
1251
1252 /**
1253 * @brief Provides access to the data contained in the %string.
1254 * @param __n The index of the character to access.
1255 * @return Read-only (const) reference to the character.
1256 * @throw std::out_of_range If @a n is an invalid index.
1257 *
1258 * This function provides for safer data access. The parameter is
1259 * first checked that it is in the range of the string. The function
1260 * throws out_of_range if the check fails.
1261 */
1262 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1263 const_reference
1264 at(size_type __n) const
1265 {
1266 if (__n >= this->size())
1267 __throw_out_of_range_fmt(__N("basic_string::at: __n "("basic_string::at: __n " "(which is %zu) >= this->size() "
"(which is %zu)")
1268 "(which is %zu) >= this->size() "("basic_string::at: __n " "(which is %zu) >= this->size() "
"(which is %zu)")
1269 "(which is %zu)")("basic_string::at: __n " "(which is %zu) >= this->size() "
"(which is %zu)")
,
1270 __n, this->size());
1271 return _M_data()[__n];
1272 }
1273
1274 /**
1275 * @brief Provides access to the data contained in the %string.
1276 * @param __n The index of the character to access.
1277 * @return Read/write reference to the character.
1278 * @throw std::out_of_range If @a n is an invalid index.
1279 *
1280 * This function provides for safer data access. The parameter is
1281 * first checked that it is in the range of the string. The function
1282 * throws out_of_range if the check fails.
1283 */
1284 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1285 reference
1286 at(size_type __n)
1287 {
1288 if (__n >= size())
1289 __throw_out_of_range_fmt(__N("basic_string::at: __n "("basic_string::at: __n " "(which is %zu) >= this->size() "
"(which is %zu)")
1290 "(which is %zu) >= this->size() "("basic_string::at: __n " "(which is %zu) >= this->size() "
"(which is %zu)")
1291 "(which is %zu)")("basic_string::at: __n " "(which is %zu) >= this->size() "
"(which is %zu)")
,
1292 __n, this->size());
1293 return _M_data()[__n];
1294 }
1295
1296#if __cplusplus202002L >= 201103L
1297 /**
1298 * Returns a read/write reference to the data at the first
1299 * element of the %string.
1300 */
1301 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1302 reference
1303 front() noexcept
1304 {
1305 __glibcxx_assert(!empty())do { if (std::__is_constant_evaluated() && !bool(!empty
())) __builtin_unreachable(); } while (false)
;
1306 return operator[](0);
1307 }
1308
1309 /**
1310 * Returns a read-only (constant) reference to the data at the first
1311 * element of the %string.
1312 */
1313 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1314 const_reference
1315 front() const noexcept
1316 {
1317 __glibcxx_assert(!empty())do { if (std::__is_constant_evaluated() && !bool(!empty
())) __builtin_unreachable(); } while (false)
;
1318 return operator[](0);
1319 }
1320
1321 /**
1322 * Returns a read/write reference to the data at the last
1323 * element of the %string.
1324 */
1325 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1326 reference
1327 back() noexcept
1328 {
1329 __glibcxx_assert(!empty())do { if (std::__is_constant_evaluated() && !bool(!empty
())) __builtin_unreachable(); } while (false)
;
1330 return operator[](this->size() - 1);
1331 }
1332
1333 /**
1334 * Returns a read-only (constant) reference to the data at the
1335 * last element of the %string.
1336 */
1337 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
1338 const_reference
1339 back() const noexcept
1340 {
1341 __glibcxx_assert(!empty())do { if (std::__is_constant_evaluated() && !bool(!empty
())) __builtin_unreachable(); } while (false)
;
1342 return operator[](this->size() - 1);
1343 }
1344#endif
1345
1346 // Modifiers:
1347 /**
1348 * @brief Append a string to this string.
1349 * @param __str The string to append.
1350 * @return Reference to this string.
1351 */
1352 _GLIBCXX20_CONSTEXPRconstexpr
1353 basic_string&
1354 operator+=(const basic_string& __str)
1355 { return this->append(__str); }
1356
1357 /**
1358 * @brief Append a C string.
1359 * @param __s The C string to append.
1360 * @return Reference to this string.
1361 */
1362 _GLIBCXX20_CONSTEXPRconstexpr
1363 basic_string&
1364 operator+=(const _CharT* __s)
1365 { return this->append(__s); }
1366
1367 /**
1368 * @brief Append a character.
1369 * @param __c The character to append.
1370 * @return Reference to this string.
1371 */
1372 _GLIBCXX20_CONSTEXPRconstexpr
1373 basic_string&
1374 operator+=(_CharT __c)
1375 {
1376 this->push_back(__c);
1377 return *this;
1378 }
1379
1380#if __cplusplus202002L >= 201103L
1381 /**
1382 * @brief Append an initializer_list of characters.
1383 * @param __l The initializer_list of characters to be appended.
1384 * @return Reference to this string.
1385 */
1386 _GLIBCXX20_CONSTEXPRconstexpr
1387 basic_string&
1388 operator+=(initializer_list<_CharT> __l)
1389 { return this->append(__l.begin(), __l.size()); }
1390#endif // C++11
1391
1392#if __cplusplus202002L >= 201703L
1393 /**
1394 * @brief Append a string_view.
1395 * @param __svt An object convertible to string_view to be appended.
1396 * @return Reference to this string.
1397 */
1398 template<typename _Tp>
1399 _GLIBCXX20_CONSTEXPRconstexpr
1400 _If_sv<_Tp, basic_string&>
1401 operator+=(const _Tp& __svt)
1402 { return this->append(__svt); }
1403#endif // C++17
1404
1405 /**
1406 * @brief Append a string to this string.
1407 * @param __str The string to append.
1408 * @return Reference to this string.
1409 */
1410 _GLIBCXX20_CONSTEXPRconstexpr
1411 basic_string&
1412 append(const basic_string& __str)
1413 { return this->append(__str._M_data(), __str.size()); }
1414
1415 /**
1416 * @brief Append a substring.
1417 * @param __str The string to append.
1418 * @param __pos Index of the first character of str to append.
1419 * @param __n The number of characters to append.
1420 * @return Reference to this string.
1421 * @throw std::out_of_range if @a __pos is not a valid index.
1422 *
1423 * This function appends @a __n characters from @a __str
1424 * starting at @a __pos to this string. If @a __n is is larger
1425 * than the number of available characters in @a __str, the
1426 * remainder of @a __str is appended.
1427 */
1428 _GLIBCXX20_CONSTEXPRconstexpr
1429 basic_string&
1430 append(const basic_string& __str, size_type __pos, size_type __n = npos)
1431 { return this->append(__str._M_data()
1432 + __str._M_check(__pos, "basic_string::append"),
1433 __str._M_limit(__pos, __n)); }
1434
1435 /**
1436 * @brief Append a C substring.
1437 * @param __s The C string to append.
1438 * @param __n The number of characters to append.
1439 * @return Reference to this string.
1440 */
1441 _GLIBCXX20_CONSTEXPRconstexpr
1442 basic_string&
1443 append(const _CharT* __s, size_type __n)
1444 {
1445 __glibcxx_requires_string_len(__s, __n);
1446 _M_check_length(size_type(0), __n, "basic_string::append");
1447 return _M_append(__s, __n);
1448 }
1449
1450 /**
1451 * @brief Append a C string.
1452 * @param __s The C string to append.
1453 * @return Reference to this string.
1454 */
1455 _GLIBCXX20_CONSTEXPRconstexpr
1456 basic_string&
1457 append(const _CharT* __s)
1458 {
1459 __glibcxx_requires_string(__s);
1460 const size_type __n = traits_type::length(__s);
1461 _M_check_length(size_type(0), __n, "basic_string::append");
1462 return _M_append(__s, __n);
1463 }
1464
1465 /**
1466 * @brief Append multiple characters.
1467 * @param __n The number of characters to append.
1468 * @param __c The character to use.
1469 * @return Reference to this string.
1470 *
1471 * Appends __n copies of __c to this string.
1472 */
1473 _GLIBCXX20_CONSTEXPRconstexpr
1474 basic_string&
1475 append(size_type __n, _CharT __c)
1476 { return _M_replace_aux(this->size(), size_type(0), __n, __c); }
1477
1478#if __cplusplus202002L >= 201103L
1479 /**
1480 * @brief Append an initializer_list of characters.
1481 * @param __l The initializer_list of characters to append.
1482 * @return Reference to this string.
1483 */
1484 _GLIBCXX20_CONSTEXPRconstexpr
1485 basic_string&
1486 append(initializer_list<_CharT> __l)
1487 { return this->append(__l.begin(), __l.size()); }
1488#endif // C++11
1489
1490 /**
1491 * @brief Append a range of characters.
1492 * @param __first Iterator referencing the first character to append.
1493 * @param __last Iterator marking the end of the range.
1494 * @return Reference to this string.
1495 *
1496 * Appends characters in the range [__first,__last) to this string.
1497 */
1498#if __cplusplus202002L >= 201103L
1499 template<class _InputIterator,
1500 typename = std::_RequireInputIter<_InputIterator>>
1501 _GLIBCXX20_CONSTEXPRconstexpr
1502#else
1503 template<class _InputIterator>
1504#endif
1505 basic_string&
1506 append(_InputIterator __first, _InputIterator __last)
1507 { return this->replace(end(), end(), __first, __last); }
1508
1509#if __cplusplus202002L >= 201703L
1510 /**
1511 * @brief Append a string_view.
1512 * @param __svt An object convertible to string_view to be appended.
1513 * @return Reference to this string.
1514 */
1515 template<typename _Tp>
1516 _GLIBCXX20_CONSTEXPRconstexpr
1517 _If_sv<_Tp, basic_string&>
1518 append(const _Tp& __svt)
1519 {
1520 __sv_type __sv = __svt;
1521 return this->append(__sv.data(), __sv.size());
1522 }
1523
1524 /**
1525 * @brief Append a range of characters from a string_view.
1526 * @param __svt An object convertible to string_view to be appended from.
1527 * @param __pos The position in the string_view to append from.
1528 * @param __n The number of characters to append from the string_view.
1529 * @return Reference to this string.
1530 */
1531 template<typename _Tp>
1532 _GLIBCXX20_CONSTEXPRconstexpr
1533 _If_sv<_Tp, basic_string&>
1534 append(const _Tp& __svt, size_type __pos, size_type __n = npos)
1535 {
1536 __sv_type __sv = __svt;
1537 return _M_append(__sv.data()
1538 + std::__sv_check(__sv.size(), __pos, "basic_string::append"),
1539 std::__sv_limit(__sv.size(), __pos, __n));
1540 }
1541#endif // C++17
1542
1543 /**
1544 * @brief Append a single character.
1545 * @param __c Character to append.
1546 */
1547 _GLIBCXX20_CONSTEXPRconstexpr
1548 void
1549 push_back(_CharT __c)
1550 {
1551 const size_type __size = this->size();
1552 if (__size + 1 > this->capacity())
1553 this->_M_mutate(__size, size_type(0), 0, size_type(1));
1554 traits_type::assign(this->_M_data()[__size], __c);
1555 this->_M_set_length(__size + 1);
1556 }
1557
1558 /**
1559 * @brief Set value to contents of another string.
1560 * @param __str Source string to use.
1561 * @return Reference to this string.
1562 */
1563 _GLIBCXX20_CONSTEXPRconstexpr
1564 basic_string&
1565 assign(const basic_string& __str)
1566 {
1567#if __cplusplus202002L >= 201103L
1568 if (_Alloc_traits::_S_propagate_on_copy_assign())
1569 {
1570 if (!_Alloc_traits::_S_always_equal() && !_M_is_local()
1571 && _M_get_allocator() != __str._M_get_allocator())
1572 {
1573 // Propagating allocator cannot free existing storage so must
1574 // deallocate it before replacing current allocator.
1575 if (__str.size() <= _S_local_capacity)
1576 {
1577 _M_destroy(_M_allocated_capacity);
1578 _M_data(_M_use_local_data());
1579 _M_set_length(0);
1580 }
1581 else
1582 {
1583 const auto __len = __str.size();
1584 auto __alloc = __str._M_get_allocator();
1585 // If this allocation throws there are no effects:
1586 auto __ptr = _S_allocate(__alloc, __len + 1);
1587 _M_destroy(_M_allocated_capacity);
1588 _M_data(__ptr);
1589 _M_capacity(__len);
1590 _M_set_length(__len);
1591 }
1592 }
1593 std::__alloc_on_copy(_M_get_allocator(), __str._M_get_allocator());
1594 }
1595#endif
1596 this->_M_assign(__str);
1597 return *this;
1598 }
1599
1600#if __cplusplus202002L >= 201103L
1601 /**
1602 * @brief Set value to contents of another string.
1603 * @param __str Source string to use.
1604 * @return Reference to this string.
1605 *
1606 * This function sets this string to the exact contents of @a __str.
1607 * @a __str is a valid, but unspecified string.
1608 */
1609 _GLIBCXX20_CONSTEXPRconstexpr
1610 basic_string&
1611 assign(basic_string&& __str)
1612 noexcept(_Alloc_traits::_S_nothrow_move())
1613 {
1614 // _GLIBCXX_RESOLVE_LIB_DEFECTS
1615 // 2063. Contradictory requirements for string move assignment
1616 return *this = std::move(__str);
1617 }
1618#endif // C++11
1619
1620 /**
1621 * @brief Set value to a substring of a string.
1622 * @param __str The string to use.
1623 * @param __pos Index of the first character of str.
1624 * @param __n Number of characters to use.
1625 * @return Reference to this string.
1626 * @throw std::out_of_range if @a pos is not a valid index.
1627 *
1628 * This function sets this string to the substring of @a __str
1629 * consisting of @a __n characters at @a __pos. If @a __n is
1630 * is larger than the number of available characters in @a
1631 * __str, the remainder of @a __str is used.
1632 */
1633 _GLIBCXX20_CONSTEXPRconstexpr
1634 basic_string&
1635 assign(const basic_string& __str, size_type __pos, size_type __n = npos)
1636 { return _M_replace(size_type(0), this->size(), __str._M_data()
1637 + __str._M_check(__pos, "basic_string::assign"),
1638 __str._M_limit(__pos, __n)); }
1639
1640 /**
1641 * @brief Set value to a C substring.
1642 * @param __s The C string to use.
1643 * @param __n Number of characters to use.
1644 * @return Reference to this string.
1645 *
1646 * This function sets the value of this string to the first @a __n
1647 * characters of @a __s. If @a __n is is larger than the number of
1648 * available characters in @a __s, the remainder of @a __s is used.
1649 */
1650 _GLIBCXX20_CONSTEXPRconstexpr
1651 basic_string&
1652 assign(const _CharT* __s, size_type __n)
1653 {
1654 __glibcxx_requires_string_len(__s, __n);
1655 return _M_replace(size_type(0), this->size(), __s, __n);
1656 }
1657
1658 /**
1659 * @brief Set value to contents of a C string.
1660 * @param __s The C string to use.
1661 * @return Reference to this string.
1662 *
1663 * This function sets the value of this string to the value of @a __s.
1664 * The data is copied, so there is no dependence on @a __s once the
1665 * function returns.
1666 */
1667 _GLIBCXX20_CONSTEXPRconstexpr
1668 basic_string&
1669 assign(const _CharT* __s)
1670 {
1671 __glibcxx_requires_string(__s);
1672 return _M_replace(size_type(0), this->size(), __s,
1673 traits_type::length(__s));
1674 }
1675
1676 /**
1677 * @brief Set value to multiple characters.
1678 * @param __n Length of the resulting string.
1679 * @param __c The character to use.
1680 * @return Reference to this string.
1681 *
1682 * This function sets the value of this string to @a __n copies of
1683 * character @a __c.
1684 */
1685 _GLIBCXX20_CONSTEXPRconstexpr
1686 basic_string&
1687 assign(size_type __n, _CharT __c)
1688 { return _M_replace_aux(size_type(0), this->size(), __n, __c); }
1689
1690 /**
1691 * @brief Set value to a range of characters.
1692 * @param __first Iterator referencing the first character to append.
1693 * @param __last Iterator marking the end of the range.
1694 * @return Reference to this string.
1695 *
1696 * Sets value of string to characters in the range [__first,__last).
1697 */
1698#if __cplusplus202002L >= 201103L
1699 template<class _InputIterator,
1700 typename = std::_RequireInputIter<_InputIterator>>
1701 _GLIBCXX20_CONSTEXPRconstexpr
1702#else
1703 template<class _InputIterator>
1704#endif
1705 basic_string&
1706 assign(_InputIterator __first, _InputIterator __last)
1707 { return this->replace(begin(), end(), __first, __last); }
1708
1709#if __cplusplus202002L >= 201103L
1710 /**
1711 * @brief Set value to an initializer_list of characters.
1712 * @param __l The initializer_list of characters to assign.
1713 * @return Reference to this string.
1714 */
1715 _GLIBCXX20_CONSTEXPRconstexpr
1716 basic_string&
1717 assign(initializer_list<_CharT> __l)
1718 { return this->assign(__l.begin(), __l.size()); }
1719#endif // C++11
1720
1721#if __cplusplus202002L >= 201703L
1722 /**
1723 * @brief Set value from a string_view.
1724 * @param __svt The source object convertible to string_view.
1725 * @return Reference to this string.
1726 */
1727 template<typename _Tp>
1728 _GLIBCXX20_CONSTEXPRconstexpr
1729 _If_sv<_Tp, basic_string&>
1730 assign(const _Tp& __svt)
1731 {
1732 __sv_type __sv = __svt;
1733 return this->assign(__sv.data(), __sv.size());
1734 }
1735
1736 /**
1737 * @brief Set value from a range of characters in a string_view.
1738 * @param __svt The source object convertible to string_view.
1739 * @param __pos The position in the string_view to assign from.
1740 * @param __n The number of characters to assign.
1741 * @return Reference to this string.
1742 */
1743 template<typename _Tp>
1744 _GLIBCXX20_CONSTEXPRconstexpr
1745 _If_sv<_Tp, basic_string&>
1746 assign(const _Tp& __svt, size_type __pos, size_type __n = npos)
1747 {
1748 __sv_type __sv = __svt;
1749 return _M_replace(size_type(0), this->size(),
1750 __sv.data()
1751 + std::__sv_check(__sv.size(), __pos, "basic_string::assign"),
1752 std::__sv_limit(__sv.size(), __pos, __n));
1753 }
1754#endif // C++17
1755
1756#if __cplusplus202002L >= 201103L
1757 /**
1758 * @brief Insert multiple characters.
1759 * @param __p Const_iterator referencing location in string to
1760 * insert at.
1761 * @param __n Number of characters to insert
1762 * @param __c The character to insert.
1763 * @return Iterator referencing the first inserted char.
1764 * @throw std::length_error If new length exceeds @c max_size().
1765 *
1766 * Inserts @a __n copies of character @a __c starting at the
1767 * position referenced by iterator @a __p. If adding
1768 * characters causes the length to exceed max_size(),
1769 * length_error is thrown. The value of the string doesn't
1770 * change if an error is thrown.
1771 */
1772 _GLIBCXX20_CONSTEXPRconstexpr
1773 iterator
1774 insert(const_iterator __p, size_type __n, _CharT __c)
1775 {
1776 _GLIBCXX_DEBUG_PEDASSERT(__p >= begin() && __p <= end());
1777 const size_type __pos = __p - begin();
1778 this->replace(__p, __p, __n, __c);
1779 return iterator(this->_M_data() + __pos);
1780 }
1781#else
1782 /**
1783 * @brief Insert multiple characters.
1784 * @param __p Iterator referencing location in string to insert at.
1785 * @param __n Number of characters to insert
1786 * @param __c The character to insert.
1787 * @throw std::length_error If new length exceeds @c max_size().
1788 *
1789 * Inserts @a __n copies of character @a __c starting at the
1790 * position referenced by iterator @a __p. If adding
1791 * characters causes the length to exceed max_size(),
1792 * length_error is thrown. The value of the string doesn't
1793 * change if an error is thrown.
1794 */
1795 void
1796 insert(iterator __p, size_type __n, _CharT __c)
1797 { this->replace(__p, __p, __n, __c); }
1798#endif
1799
1800#if __cplusplus202002L >= 201103L
1801 /**
1802 * @brief Insert a range of characters.
1803 * @param __p Const_iterator referencing location in string to
1804 * insert at.
1805 * @param __beg Start of range.
1806 * @param __end End of range.
1807 * @return Iterator referencing the first inserted char.
1808 * @throw std::length_error If new length exceeds @c max_size().
1809 *
1810 * Inserts characters in range [beg,end). If adding characters
1811 * causes the length to exceed max_size(), length_error is
1812 * thrown. The value of the string doesn't change if an error
1813 * is thrown.
1814 */
1815 template<class _InputIterator,
1816 typename = std::_RequireInputIter<_InputIterator>>
1817 _GLIBCXX20_CONSTEXPRconstexpr
1818 iterator
1819 insert(const_iterator __p, _InputIterator __beg, _InputIterator __end)
1820 {
1821 _GLIBCXX_DEBUG_PEDASSERT(__p >= begin() && __p <= end());
1822 const size_type __pos = __p - begin();
1823 this->replace(__p, __p, __beg, __end);
1824 return iterator(this->_M_data() + __pos);
1825 }
1826#else
1827 /**
1828 * @brief Insert a range of characters.
1829 * @param __p Iterator referencing location in string to insert at.
1830 * @param __beg Start of range.
1831 * @param __end End of range.
1832 * @throw std::length_error If new length exceeds @c max_size().
1833 *
1834 * Inserts characters in range [__beg,__end). If adding
1835 * characters causes the length to exceed max_size(),
1836 * length_error is thrown. The value of the string doesn't
1837 * change if an error is thrown.
1838 */
1839 template<class _InputIterator>
1840 void
1841 insert(iterator __p, _InputIterator __beg, _InputIterator __end)
1842 { this->replace(__p, __p, __beg, __end); }
1843#endif
1844
1845#if __cplusplus202002L >= 201103L
1846 /**
1847 * @brief Insert an initializer_list of characters.
1848 * @param __p Iterator referencing location in string to insert at.
1849 * @param __l The initializer_list of characters to insert.
1850 * @throw std::length_error If new length exceeds @c max_size().
1851 */
1852 _GLIBCXX20_CONSTEXPRconstexpr
1853 iterator
1854 insert(const_iterator __p, initializer_list<_CharT> __l)
1855 { return this->insert(__p, __l.begin(), __l.end()); }
1856
1857#ifdef _GLIBCXX_DEFINING_STRING_INSTANTIATIONS
1858 // See PR libstdc++/83328
1859 void
1860 insert(iterator __p, initializer_list<_CharT> __l)
1861 {
1862 _GLIBCXX_DEBUG_PEDASSERT(__p >= begin() && __p <= end());
1863 this->insert(__p - begin(), __l.begin(), __l.size());
1864 }
1865#endif
1866#endif // C++11
1867
1868 /**
1869 * @brief Insert value of a string.
1870 * @param __pos1 Position in string to insert at.
1871 * @param __str The string to insert.
1872 * @return Reference to this string.
1873 * @throw std::length_error If new length exceeds @c max_size().
1874 *
1875 * Inserts value of @a __str starting at @a __pos1. If adding
1876 * characters causes the length to exceed max_size(),
1877 * length_error is thrown. The value of the string doesn't
1878 * change if an error is thrown.
1879 */
1880 _GLIBCXX20_CONSTEXPRconstexpr
1881 basic_string&
1882 insert(size_type __pos1, const basic_string& __str)
1883 { return this->replace(__pos1, size_type(0),
1884 __str._M_data(), __str.size()); }
1885
1886 /**
1887 * @brief Insert a substring.
1888 * @param __pos1 Position in string to insert at.
1889 * @param __str The string to insert.
1890 * @param __pos2 Start of characters in str to insert.
1891 * @param __n Number of characters to insert.
1892 * @return Reference to this string.
1893 * @throw std::length_error If new length exceeds @c max_size().
1894 * @throw std::out_of_range If @a pos1 > size() or
1895 * @a __pos2 > @a str.size().
1896 *
1897 * Starting at @a pos1, insert @a __n character of @a __str
1898 * beginning with @a __pos2. If adding characters causes the
1899 * length to exceed max_size(), length_error is thrown. If @a
1900 * __pos1 is beyond the end of this string or @a __pos2 is
1901 * beyond the end of @a __str, out_of_range is thrown. The
1902 * value of the string doesn't change if an error is thrown.
1903 */
1904 _GLIBCXX20_CONSTEXPRconstexpr
1905 basic_string&
1906 insert(size_type __pos1, const basic_string& __str,
1907 size_type __pos2, size_type __n = npos)
1908 { return this->replace(__pos1, size_type(0), __str._M_data()
1909 + __str._M_check(__pos2, "basic_string::insert"),
1910 __str._M_limit(__pos2, __n)); }
1911
1912 /**
1913 * @brief Insert a C substring.
1914 * @param __pos Position in string to insert at.
1915 * @param __s The C string to insert.
1916 * @param __n The number of characters to insert.
1917 * @return Reference to this string.
1918 * @throw std::length_error If new length exceeds @c max_size().
1919 * @throw std::out_of_range If @a __pos is beyond the end of this
1920 * string.
1921 *
1922 * Inserts the first @a __n characters of @a __s starting at @a
1923 * __pos. If adding characters causes the length to exceed
1924 * max_size(), length_error is thrown. If @a __pos is beyond
1925 * end(), out_of_range is thrown. The value of the string
1926 * doesn't change if an error is thrown.
1927 */
1928 _GLIBCXX20_CONSTEXPRconstexpr
1929 basic_string&
1930 insert(size_type __pos, const _CharT* __s, size_type __n)
1931 { return this->replace(__pos, size_type(0), __s, __n); }
1932
1933 /**
1934 * @brief Insert a C string.
1935 * @param __pos Position in string to insert at.
1936 * @param __s The C string to insert.
1937 * @return Reference to this string.
1938 * @throw std::length_error If new length exceeds @c max_size().
1939 * @throw std::out_of_range If @a pos is beyond the end of this
1940 * string.
1941 *
1942 * Inserts the first @a n characters of @a __s starting at @a __pos. If
1943 * adding characters causes the length to exceed max_size(),
1944 * length_error is thrown. If @a __pos is beyond end(), out_of_range is
1945 * thrown. The value of the string doesn't change if an error is
1946 * thrown.
1947 */
1948 _GLIBCXX20_CONSTEXPRconstexpr
1949 basic_string&
1950 insert(size_type __pos, const _CharT* __s)
1951 {
1952 __glibcxx_requires_string(__s);
1953 return this->replace(__pos, size_type(0), __s,
1954 traits_type::length(__s));
1955 }
1956
1957 /**
1958 * @brief Insert multiple characters.
1959 * @param __pos Index in string to insert at.
1960 * @param __n Number of characters to insert
1961 * @param __c The character to insert.
1962 * @return Reference to this string.
1963 * @throw std::length_error If new length exceeds @c max_size().
1964 * @throw std::out_of_range If @a __pos is beyond the end of this
1965 * string.
1966 *
1967 * Inserts @a __n copies of character @a __c starting at index
1968 * @a __pos. If adding characters causes the length to exceed
1969 * max_size(), length_error is thrown. If @a __pos > length(),
1970 * out_of_range is thrown. The value of the string doesn't
1971 * change if an error is thrown.
1972 */
1973 _GLIBCXX20_CONSTEXPRconstexpr
1974 basic_string&
1975 insert(size_type __pos, size_type __n, _CharT __c)
1976 { return _M_replace_aux(_M_check(__pos, "basic_string::insert"),
1977 size_type(0), __n, __c); }
1978
1979 /**
1980 * @brief Insert one character.
1981 * @param __p Iterator referencing position in string to insert at.
1982 * @param __c The character to insert.
1983 * @return Iterator referencing newly inserted char.
1984 * @throw std::length_error If new length exceeds @c max_size().
1985 *
1986 * Inserts character @a __c at position referenced by @a __p.
1987 * If adding character causes the length to exceed max_size(),
1988 * length_error is thrown. If @a __p is beyond end of string,
1989 * out_of_range is thrown. The value of the string doesn't
1990 * change if an error is thrown.
1991 */
1992 _GLIBCXX20_CONSTEXPRconstexpr
1993 iterator
1994 insert(__const_iterator __p, _CharT __c)
1995 {
1996 _GLIBCXX_DEBUG_PEDASSERT(__p >= begin() && __p <= end());
1997 const size_type __pos = __p - begin();
1998 _M_replace_aux(__pos, size_type(0), size_type(1), __c);
1999 return iterator(_M_data() + __pos);
2000 }
2001
2002#if __cplusplus202002L >= 201703L
2003 /**
2004 * @brief Insert a string_view.
2005 * @param __pos Position in string to insert at.
2006 * @param __svt The object convertible to string_view to insert.
2007 * @return Reference to this string.
2008 */
2009 template<typename _Tp>
2010 _GLIBCXX20_CONSTEXPRconstexpr
2011 _If_sv<_Tp, basic_string&>
2012 insert(size_type __pos, const _Tp& __svt)
2013 {
2014 __sv_type __sv = __svt;
2015 return this->insert(__pos, __sv.data(), __sv.size());
2016 }
2017
2018 /**
2019 * @brief Insert a string_view.
2020 * @param __pos1 Position in string to insert at.
2021 * @param __svt The object convertible to string_view to insert from.
2022 * @param __pos2 Start of characters in str to insert.
2023 * @param __n The number of characters to insert.
2024 * @return Reference to this string.
2025 */
2026 template<typename _Tp>
2027 _GLIBCXX20_CONSTEXPRconstexpr
2028 _If_sv<_Tp, basic_string&>
2029 insert(size_type __pos1, const _Tp& __svt,
2030 size_type __pos2, size_type __n = npos)
2031 {
2032 __sv_type __sv = __svt;
2033 return this->replace(__pos1, size_type(0),
2034 __sv.data()
2035 + std::__sv_check(__sv.size(), __pos2, "basic_string::insert"),
2036 std::__sv_limit(__sv.size(), __pos2, __n));
2037 }
2038#endif // C++17
2039
2040 /**
2041 * @brief Remove characters.
2042 * @param __pos Index of first character to remove (default 0).
2043 * @param __n Number of characters to remove (default remainder).
2044 * @return Reference to this string.
2045 * @throw std::out_of_range If @a pos is beyond the end of this
2046 * string.
2047 *
2048 * Removes @a __n characters from this string starting at @a
2049 * __pos. The length of the string is reduced by @a __n. If
2050 * there are < @a __n characters to remove, the remainder of
2051 * the string is truncated. If @a __p is beyond end of string,
2052 * out_of_range is thrown. The value of the string doesn't
2053 * change if an error is thrown.
2054 */
2055 _GLIBCXX20_CONSTEXPRconstexpr
2056 basic_string&
2057 erase(size_type __pos = 0, size_type __n = npos)
2058 {
2059 _M_check(__pos, "basic_string::erase");
2060 if (__n == npos)
2061 this->_M_set_length(__pos);
2062 else if (__n != 0)
2063 this->_M_erase(__pos, _M_limit(__pos, __n));
2064 return *this;
2065 }
2066
2067 /**
2068 * @brief Remove one character.
2069 * @param __position Iterator referencing the character to remove.
2070 * @return iterator referencing same location after removal.
2071 *
2072 * Removes the character at @a __position from this string. The value
2073 * of the string doesn't change if an error is thrown.
2074 */
2075 _GLIBCXX20_CONSTEXPRconstexpr
2076 iterator
2077 erase(__const_iterator __position)
2078 {
2079 _GLIBCXX_DEBUG_PEDASSERT(__position >= begin()
2080 && __position < end());
2081 const size_type __pos = __position - begin();
2082 this->_M_erase(__pos, size_type(1));
2083 return iterator(_M_data() + __pos);
2084 }
2085
2086 /**
2087 * @brief Remove a range of characters.
2088 * @param __first Iterator referencing the first character to remove.
2089 * @param __last Iterator referencing the end of the range.
2090 * @return Iterator referencing location of first after removal.
2091 *
2092 * Removes the characters in the range [first,last) from this string.
2093 * The value of the string doesn't change if an error is thrown.
2094 */
2095 _GLIBCXX20_CONSTEXPRconstexpr
2096 iterator
2097 erase(__const_iterator __first, __const_iterator __last)
2098 {
2099 _GLIBCXX_DEBUG_PEDASSERT(__first >= begin() && __first <= __last
2100 && __last <= end());
2101 const size_type __pos = __first - begin();
2102 if (__last == end())
2103 this->_M_set_length(__pos);
2104 else
2105 this->_M_erase(__pos, __last - __first);
2106 return iterator(this->_M_data() + __pos);
2107 }
2108
2109#if __cplusplus202002L >= 201103L
2110 /**
2111 * @brief Remove the last character.
2112 *
2113 * The string must be non-empty.
2114 */
2115 _GLIBCXX20_CONSTEXPRconstexpr
2116 void
2117 pop_back() noexcept
2118 {
2119 __glibcxx_assert(!empty())do { if (std::__is_constant_evaluated() && !bool(!empty
())) __builtin_unreachable(); } while (false)
;
2120 _M_erase(size() - 1, 1);
2121 }
2122#endif // C++11
2123
2124 /**
2125 * @brief Replace characters with value from another string.
2126 * @param __pos Index of first character to replace.
2127 * @param __n Number of characters to be replaced.
2128 * @param __str String to insert.
2129 * @return Reference to this string.
2130 * @throw std::out_of_range If @a pos is beyond the end of this
2131 * string.
2132 * @throw std::length_error If new length exceeds @c max_size().
2133 *
2134 * Removes the characters in the range [__pos,__pos+__n) from
2135 * this string. In place, the value of @a __str is inserted.
2136 * If @a __pos is beyond end of string, out_of_range is thrown.
2137 * If the length of the result exceeds max_size(), length_error
2138 * is thrown. The value of the string doesn't change if an
2139 * error is thrown.
2140 */
2141 _GLIBCXX20_CONSTEXPRconstexpr
2142 basic_string&
2143 replace(size_type __pos, size_type __n, const basic_string& __str)
2144 { return this->replace(__pos, __n, __str._M_data(), __str.size()); }
2145
2146 /**
2147 * @brief Replace characters with value from another string.
2148 * @param __pos1 Index of first character to replace.
2149 * @param __n1 Number of characters to be replaced.
2150 * @param __str String to insert.
2151 * @param __pos2 Index of first character of str to use.
2152 * @param __n2 Number of characters from str to use.
2153 * @return Reference to this string.
2154 * @throw std::out_of_range If @a __pos1 > size() or @a __pos2 >
2155 * __str.size().
2156 * @throw std::length_error If new length exceeds @c max_size().
2157 *
2158 * Removes the characters in the range [__pos1,__pos1 + n) from this
2159 * string. In place, the value of @a __str is inserted. If @a __pos is
2160 * beyond end of string, out_of_range is thrown. If the length of the
2161 * result exceeds max_size(), length_error is thrown. The value of the
2162 * string doesn't change if an error is thrown.
2163 */
2164 _GLIBCXX20_CONSTEXPRconstexpr
2165 basic_string&
2166 replace(size_type __pos1, size_type __n1, const basic_string& __str,
2167 size_type __pos2, size_type __n2 = npos)
2168 { return this->replace(__pos1, __n1, __str._M_data()
2169 + __str._M_check(__pos2, "basic_string::replace"),
2170 __str._M_limit(__pos2, __n2)); }
2171
2172 /**
2173 * @brief Replace characters with value of a C substring.
2174 * @param __pos Index of first character to replace.
2175 * @param __n1 Number of characters to be replaced.
2176 * @param __s C string to insert.
2177 * @param __n2 Number of characters from @a s to use.
2178 * @return Reference to this string.
2179 * @throw std::out_of_range If @a pos1 > size().
2180 * @throw std::length_error If new length exceeds @c max_size().
2181 *
2182 * Removes the characters in the range [__pos,__pos + __n1)
2183 * from this string. In place, the first @a __n2 characters of
2184 * @a __s are inserted, or all of @a __s if @a __n2 is too large. If
2185 * @a __pos is beyond end of string, out_of_range is thrown. If
2186 * the length of result exceeds max_size(), length_error is
2187 * thrown. The value of the string doesn't change if an error
2188 * is thrown.
2189 */
2190 _GLIBCXX20_CONSTEXPRconstexpr
2191 basic_string&
2192 replace(size_type __pos, size_type __n1, const _CharT* __s,
2193 size_type __n2)
2194 {
2195 __glibcxx_requires_string_len(__s, __n2);
2196 return _M_replace(_M_check(__pos, "basic_string::replace"),
2197 _M_limit(__pos, __n1), __s, __n2);
2198 }
2199
2200 /**
2201 * @brief Replace characters with value of a C string.
2202 * @param __pos Index of first character to replace.
2203 * @param __n1 Number of characters to be replaced.
2204 * @param __s C string to insert.
2205 * @return Reference to this string.
2206 * @throw std::out_of_range If @a pos > size().
2207 * @throw std::length_error If new length exceeds @c max_size().
2208 *
2209 * Removes the characters in the range [__pos,__pos + __n1)
2210 * from this string. In place, the characters of @a __s are
2211 * inserted. If @a __pos is beyond end of string, out_of_range
2212 * is thrown. If the length of result exceeds max_size(),
2213 * length_error is thrown. The value of the string doesn't
2214 * change if an error is thrown.
2215 */
2216 _GLIBCXX20_CONSTEXPRconstexpr
2217 basic_string&
2218 replace(size_type __pos, size_type __n1, const _CharT* __s)
2219 {
2220 __glibcxx_requires_string(__s);
2221 return this->replace(__pos, __n1, __s, traits_type::length(__s));
2222 }
2223
2224 /**
2225 * @brief Replace characters with multiple characters.
2226 * @param __pos Index of first character to replace.
2227 * @param __n1 Number of characters to be replaced.
2228 * @param __n2 Number of characters to insert.
2229 * @param __c Character to insert.
2230 * @return Reference to this string.
2231 * @throw std::out_of_range If @a __pos > size().
2232 * @throw std::length_error If new length exceeds @c max_size().
2233 *
2234 * Removes the characters in the range [pos,pos + n1) from this
2235 * string. In place, @a __n2 copies of @a __c are inserted.
2236 * If @a __pos is beyond end of string, out_of_range is thrown.
2237 * If the length of result exceeds max_size(), length_error is
2238 * thrown. The value of the string doesn't change if an error
2239 * is thrown.
2240 */
2241 _GLIBCXX20_CONSTEXPRconstexpr
2242 basic_string&
2243 replace(size_type __pos, size_type __n1, size_type __n2, _CharT __c)
2244 { return _M_replace_aux(_M_check(__pos, "basic_string::replace"),
2245 _M_limit(__pos, __n1), __n2, __c); }
2246
2247 /**
2248 * @brief Replace range of characters with string.
2249 * @param __i1 Iterator referencing start of range to replace.
2250 * @param __i2 Iterator referencing end of range to replace.
2251 * @param __str String value to insert.
2252 * @return Reference to this string.
2253 * @throw std::length_error If new length exceeds @c max_size().
2254 *
2255 * Removes the characters in the range [__i1,__i2). In place,
2256 * the value of @a __str is inserted. If the length of result
2257 * exceeds max_size(), length_error is thrown. The value of
2258 * the string doesn't change if an error is thrown.
2259 */
2260 _GLIBCXX20_CONSTEXPRconstexpr
2261 basic_string&
2262 replace(__const_iterator __i1, __const_iterator __i2,
2263 const basic_string& __str)
2264 { return this->replace(__i1, __i2, __str._M_data(), __str.size()); }
2265
2266 /**
2267 * @brief Replace range of characters with C substring.
2268 * @param __i1 Iterator referencing start of range to replace.
2269 * @param __i2 Iterator referencing end of range to replace.
2270 * @param __s C string value to insert.
2271 * @param __n Number of characters from s to insert.
2272 * @return Reference to this string.
2273 * @throw std::length_error If new length exceeds @c max_size().
2274 *
2275 * Removes the characters in the range [__i1,__i2). In place,
2276 * the first @a __n characters of @a __s are inserted. If the
2277 * length of result exceeds max_size(), length_error is thrown.
2278 * The value of the string doesn't change if an error is
2279 * thrown.
2280 */
2281 _GLIBCXX20_CONSTEXPRconstexpr
2282 basic_string&
2283 replace(__const_iterator __i1, __const_iterator __i2,
2284 const _CharT* __s, size_type __n)
2285 {
2286 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2287 && __i2 <= end());
2288 return this->replace(__i1 - begin(), __i2 - __i1, __s, __n);
2289 }
2290
2291 /**
2292 * @brief Replace range of characters with C string.
2293 * @param __i1 Iterator referencing start of range to replace.
2294 * @param __i2 Iterator referencing end of range to replace.
2295 * @param __s C string value to insert.
2296 * @return Reference to this string.
2297 * @throw std::length_error If new length exceeds @c max_size().
2298 *
2299 * Removes the characters in the range [__i1,__i2). In place,
2300 * the characters of @a __s are inserted. If the length of
2301 * result exceeds max_size(), length_error is thrown. The
2302 * value of the string doesn't change if an error is thrown.
2303 */
2304 _GLIBCXX20_CONSTEXPRconstexpr
2305 basic_string&
2306 replace(__const_iterator __i1, __const_iterator __i2, const _CharT* __s)
2307 {
2308 __glibcxx_requires_string(__s);
2309 return this->replace(__i1, __i2, __s, traits_type::length(__s));
2310 }
2311
2312 /**
2313 * @brief Replace range of characters with multiple characters
2314 * @param __i1 Iterator referencing start of range to replace.
2315 * @param __i2 Iterator referencing end of range to replace.
2316 * @param __n Number of characters to insert.
2317 * @param __c Character to insert.
2318 * @return Reference to this string.
2319 * @throw std::length_error If new length exceeds @c max_size().
2320 *
2321 * Removes the characters in the range [__i1,__i2). In place,
2322 * @a __n copies of @a __c are inserted. If the length of
2323 * result exceeds max_size(), length_error is thrown. The
2324 * value of the string doesn't change if an error is thrown.
2325 */
2326 _GLIBCXX20_CONSTEXPRconstexpr
2327 basic_string&
2328 replace(__const_iterator __i1, __const_iterator __i2, size_type __n,
2329 _CharT __c)
2330 {
2331 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2332 && __i2 <= end());
2333 return _M_replace_aux(__i1 - begin(), __i2 - __i1, __n, __c);
2334 }
2335
2336 /**
2337 * @brief Replace range of characters with range.
2338 * @param __i1 Iterator referencing start of range to replace.
2339 * @param __i2 Iterator referencing end of range to replace.
2340 * @param __k1 Iterator referencing start of range to insert.
2341 * @param __k2 Iterator referencing end of range to insert.
2342 * @return Reference to this string.
2343 * @throw std::length_error If new length exceeds @c max_size().
2344 *
2345 * Removes the characters in the range [__i1,__i2). In place,
2346 * characters in the range [__k1,__k2) are inserted. If the
2347 * length of result exceeds max_size(), length_error is thrown.
2348 * The value of the string doesn't change if an error is
2349 * thrown.
2350 */
2351#if __cplusplus202002L >= 201103L
2352 template<class _InputIterator,
2353 typename = std::_RequireInputIter<_InputIterator>>
2354 _GLIBCXX20_CONSTEXPRconstexpr
2355 basic_string&
2356 replace(const_iterator __i1, const_iterator __i2,
2357 _InputIterator __k1, _InputIterator __k2)
2358 {
2359 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2360 && __i2 <= end());
2361 __glibcxx_requires_valid_range(__k1, __k2);
2362 return this->_M_replace_dispatch(__i1, __i2, __k1, __k2,
2363 std::__false_type());
2364 }
2365#else
2366 template<class _InputIterator>
2367#ifdef _GLIBCXX_DISAMBIGUATE_REPLACE_INST
2368 typename __enable_if_not_native_iterator<_InputIterator>::__type
2369#else
2370 basic_string&
2371#endif
2372 replace(iterator __i1, iterator __i2,
2373 _InputIterator __k1, _InputIterator __k2)
2374 {
2375 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2376 && __i2 <= end());
2377 __glibcxx_requires_valid_range(__k1, __k2);
2378 typedef typename std::__is_integer<_InputIterator>::__type _Integral;
2379 return _M_replace_dispatch(__i1, __i2, __k1, __k2, _Integral());
2380 }
2381#endif
2382
2383 // Specializations for the common case of pointer and iterator:
2384 // useful to avoid the overhead of temporary buffering in _M_replace.
2385 _GLIBCXX20_CONSTEXPRconstexpr
2386 basic_string&
2387 replace(__const_iterator __i1, __const_iterator __i2,
2388 _CharT* __k1, _CharT* __k2)
2389 {
2390 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2391 && __i2 <= end());
2392 __glibcxx_requires_valid_range(__k1, __k2);
2393 return this->replace(__i1 - begin(), __i2 - __i1,
2394 __k1, __k2 - __k1);
2395 }
2396
2397 _GLIBCXX20_CONSTEXPRconstexpr
2398 basic_string&
2399 replace(__const_iterator __i1, __const_iterator __i2,
2400 const _CharT* __k1, const _CharT* __k2)
2401 {
2402 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2403 && __i2 <= end());
2404 __glibcxx_requires_valid_range(__k1, __k2);
2405 return this->replace(__i1 - begin(), __i2 - __i1,
2406 __k1, __k2 - __k1);
2407 }
2408
2409 _GLIBCXX20_CONSTEXPRconstexpr
2410 basic_string&
2411 replace(__const_iterator __i1, __const_iterator __i2,
2412 iterator __k1, iterator __k2)
2413 {
2414 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2415 && __i2 <= end());
2416 __glibcxx_requires_valid_range(__k1, __k2);
2417 return this->replace(__i1 - begin(), __i2 - __i1,
2418 __k1.base(), __k2 - __k1);
2419 }
2420
2421 _GLIBCXX20_CONSTEXPRconstexpr
2422 basic_string&
2423 replace(__const_iterator __i1, __const_iterator __i2,
2424 const_iterator __k1, const_iterator __k2)
2425 {
2426 _GLIBCXX_DEBUG_PEDASSERT(begin() <= __i1 && __i1 <= __i2
2427 && __i2 <= end());
2428 __glibcxx_requires_valid_range(__k1, __k2);
2429 return this->replace(__i1 - begin(), __i2 - __i1,
2430 __k1.base(), __k2 - __k1);
2431 }
2432
2433#if __cplusplus202002L >= 201103L
2434 /**
2435 * @brief Replace range of characters with initializer_list.
2436 * @param __i1 Iterator referencing start of range to replace.
2437 * @param __i2 Iterator referencing end of range to replace.
2438 * @param __l The initializer_list of characters to insert.
2439 * @return Reference to this string.
2440 * @throw std::length_error If new length exceeds @c max_size().
2441 *
2442 * Removes the characters in the range [__i1,__i2). In place,
2443 * characters in the range [__k1,__k2) are inserted. If the
2444 * length of result exceeds max_size(), length_error is thrown.
2445 * The value of the string doesn't change if an error is
2446 * thrown.
2447 */
2448 _GLIBCXX20_CONSTEXPRconstexpr
2449 basic_string& replace(const_iterator __i1, const_iterator __i2,
2450 initializer_list<_CharT> __l)
2451 { return this->replace(__i1, __i2, __l.begin(), __l.size()); }
2452#endif // C++11
2453
2454#if __cplusplus202002L >= 201703L
2455 /**
2456 * @brief Replace range of characters with string_view.
2457 * @param __pos The position to replace at.
2458 * @param __n The number of characters to replace.
2459 * @param __svt The object convertible to string_view to insert.
2460 * @return Reference to this string.
2461 */
2462 template<typename _Tp>
2463 _GLIBCXX20_CONSTEXPRconstexpr
2464 _If_sv<_Tp, basic_string&>
2465 replace(size_type __pos, size_type __n, const _Tp& __svt)
2466 {
2467 __sv_type __sv = __svt;
2468 return this->replace(__pos, __n, __sv.data(), __sv.size());
2469 }
2470
2471 /**
2472 * @brief Replace range of characters with string_view.
2473 * @param __pos1 The position to replace at.
2474 * @param __n1 The number of characters to replace.
2475 * @param __svt The object convertible to string_view to insert from.
2476 * @param __pos2 The position in the string_view to insert from.
2477 * @param __n2 The number of characters to insert.
2478 * @return Reference to this string.
2479 */
2480 template<typename _Tp>
2481 _GLIBCXX20_CONSTEXPRconstexpr
2482 _If_sv<_Tp, basic_string&>
2483 replace(size_type __pos1, size_type __n1, const _Tp& __svt,
2484 size_type __pos2, size_type __n2 = npos)
2485 {
2486 __sv_type __sv = __svt;
2487 return this->replace(__pos1, __n1,
2488 __sv.data()
2489 + std::__sv_check(__sv.size(), __pos2, "basic_string::replace"),
2490 std::__sv_limit(__sv.size(), __pos2, __n2));
2491 }
2492
2493 /**
2494 * @brief Replace range of characters with string_view.
2495 * @param __i1 An iterator referencing the start position
2496 to replace at.
2497 * @param __i2 An iterator referencing the end position
2498 for the replace.
2499 * @param __svt The object convertible to string_view to insert from.
2500 * @return Reference to this string.
2501 */
2502 template<typename _Tp>
2503 _GLIBCXX20_CONSTEXPRconstexpr
2504 _If_sv<_Tp, basic_string&>
2505 replace(const_iterator __i1, const_iterator __i2, const _Tp& __svt)
2506 {
2507 __sv_type __sv = __svt;
2508 return this->replace(__i1 - begin(), __i2 - __i1, __sv);
2509 }
2510#endif // C++17
2511
2512 private:
2513 template<class _Integer>
2514 _GLIBCXX20_CONSTEXPRconstexpr
2515 basic_string&
2516 _M_replace_dispatch(const_iterator __i1, const_iterator __i2,
2517 _Integer __n, _Integer __val, __true_type)
2518 { return _M_replace_aux(__i1 - begin(), __i2 - __i1, __n, __val); }
2519
2520 template<class _InputIterator>
2521 _GLIBCXX20_CONSTEXPRconstexpr
2522 basic_string&
2523 _M_replace_dispatch(const_iterator __i1, const_iterator __i2,
2524 _InputIterator __k1, _InputIterator __k2,
2525 __false_type);
2526
2527 _GLIBCXX20_CONSTEXPRconstexpr
2528 basic_string&
2529 _M_replace_aux(size_type __pos1, size_type __n1, size_type __n2,
2530 _CharT __c);
2531
2532 __attribute__((__noinline__, __noclone__, __cold__)) void
2533 _M_replace_cold(pointer __p, size_type __len1, const _CharT* __s,
2534 const size_type __len2, const size_type __how_much);
2535
2536 _GLIBCXX20_CONSTEXPRconstexpr
2537 basic_string&
2538 _M_replace(size_type __pos, size_type __len1, const _CharT* __s,
2539 const size_type __len2);
2540
2541 _GLIBCXX20_CONSTEXPRconstexpr
2542 basic_string&
2543 _M_append(const _CharT* __s, size_type __n);
2544
2545 public:
2546
2547 /**
2548 * @brief Copy substring into C string.
2549 * @param __s C string to copy value into.
2550 * @param __n Number of characters to copy.
2551 * @param __pos Index of first character to copy.
2552 * @return Number of characters actually copied
2553 * @throw std::out_of_range If __pos > size().
2554 *
2555 * Copies up to @a __n characters starting at @a __pos into the
2556 * C string @a __s. If @a __pos is %greater than size(),
2557 * out_of_range is thrown.
2558 */
2559 _GLIBCXX20_CONSTEXPRconstexpr
2560 size_type
2561 copy(_CharT* __s, size_type __n, size_type __pos = 0) const;
2562
2563 /**
2564 * @brief Swap contents with another string.
2565 * @param __s String to swap with.
2566 *
2567 * Exchanges the contents of this string with that of @a __s in constant
2568 * time.
2569 */
2570 _GLIBCXX20_CONSTEXPRconstexpr
2571 void
2572 swap(basic_string& __s) _GLIBCXX_NOEXCEPTnoexcept;
2573
2574 // String operations:
2575 /**
2576 * @brief Return const pointer to null-terminated contents.
2577 *
2578 * This is a handle to internal data. Do not modify or dire things may
2579 * happen.
2580 */
2581 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2582 const _CharT*
2583 c_str() const _GLIBCXX_NOEXCEPTnoexcept
2584 { return _M_data(); }
2585
2586 /**
2587 * @brief Return const pointer to contents.
2588 *
2589 * This is a pointer to internal data. It is undefined to modify
2590 * the contents through the returned pointer. To get a pointer that
2591 * allows modifying the contents use @c &str[0] instead,
2592 * (or in C++17 the non-const @c str.data() overload).
2593 */
2594 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2595 const _CharT*
2596 data() const _GLIBCXX_NOEXCEPTnoexcept
2597 { return _M_data(); }
2598
2599#if __cplusplus202002L >= 201703L
2600 /**
2601 * @brief Return non-const pointer to contents.
2602 *
2603 * This is a pointer to the character sequence held by the string.
2604 * Modifying the characters in the sequence is allowed.
2605 */
2606 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2607 _CharT*
2608 data() noexcept
2609 { return _M_data(); }
2610#endif
2611
2612 /**
2613 * @brief Return copy of allocator used to construct this string.
2614 */
2615 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2616 allocator_type
2617 get_allocator() const _GLIBCXX_NOEXCEPTnoexcept
2618 { return _M_get_allocator(); }
2619
2620 /**
2621 * @brief Find position of a C substring.
2622 * @param __s C string to locate.
2623 * @param __pos Index of character to search from.
2624 * @param __n Number of characters from @a s to search for.
2625 * @return Index of start of first occurrence.
2626 *
2627 * Starting from @a __pos, searches forward for the first @a
2628 * __n characters in @a __s within this string. If found,
2629 * returns the index where it begins. If not found, returns
2630 * npos.
2631 */
2632 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2633 size_type
2634 find(const _CharT* __s, size_type __pos, size_type __n) const
2635 _GLIBCXX_NOEXCEPTnoexcept;
2636
2637 /**
2638 * @brief Find position of a string.
2639 * @param __str String to locate.
2640 * @param __pos Index of character to search from (default 0).
2641 * @return Index of start of first occurrence.
2642 *
2643 * Starting from @a __pos, searches forward for value of @a __str within
2644 * this string. If found, returns the index where it begins. If not
2645 * found, returns npos.
2646 */
2647 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2648 size_type
2649 find(const basic_string& __str, size_type __pos = 0) const
2650 _GLIBCXX_NOEXCEPTnoexcept
2651 { return this->find(__str.data(), __pos, __str.size()); }
2652
2653#if __cplusplus202002L >= 201703L
2654 /**
2655 * @brief Find position of a string_view.
2656 * @param __svt The object convertible to string_view to locate.
2657 * @param __pos Index of character to search from (default 0).
2658 * @return Index of start of first occurrence.
2659 */
2660 template<typename _Tp>
2661 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2662 _If_sv<_Tp, size_type>
2663 find(const _Tp& __svt, size_type __pos = 0) const
2664 noexcept(is_same<_Tp, __sv_type>::value)
2665 {
2666 __sv_type __sv = __svt;
2667 return this->find(__sv.data(), __pos, __sv.size());
2668 }
2669#endif // C++17
2670
2671 /**
2672 * @brief Find position of a C string.
2673 * @param __s C string to locate.
2674 * @param __pos Index of character to search from (default 0).
2675 * @return Index of start of first occurrence.
2676 *
2677 * Starting from @a __pos, searches forward for the value of @a
2678 * __s within this string. If found, returns the index where
2679 * it begins. If not found, returns npos.
2680 */
2681 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2682 size_type
2683 find(const _CharT* __s, size_type __pos = 0) const _GLIBCXX_NOEXCEPTnoexcept
2684 {
2685 __glibcxx_requires_string(__s);
2686 return this->find(__s, __pos, traits_type::length(__s));
2687 }
2688
2689 /**
2690 * @brief Find position of a character.
2691 * @param __c Character to locate.
2692 * @param __pos Index of character to search from (default 0).
2693 * @return Index of first occurrence.
2694 *
2695 * Starting from @a __pos, searches forward for @a __c within
2696 * this string. If found, returns the index where it was
2697 * found. If not found, returns npos.
2698 */
2699 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2700 size_type
2701 find(_CharT __c, size_type __pos = 0) const _GLIBCXX_NOEXCEPTnoexcept;
2702
2703 /**
2704 * @brief Find last position of a string.
2705 * @param __str String to locate.
2706 * @param __pos Index of character to search back from (default end).
2707 * @return Index of start of last occurrence.
2708 *
2709 * Starting from @a __pos, searches backward for value of @a
2710 * __str within this string. If found, returns the index where
2711 * it begins. If not found, returns npos.
2712 */
2713 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2714 size_type
2715 rfind(const basic_string& __str, size_type __pos = npos) const
2716 _GLIBCXX_NOEXCEPTnoexcept
2717 { return this->rfind(__str.data(), __pos, __str.size()); }
2718
2719#if __cplusplus202002L >= 201703L
2720 /**
2721 * @brief Find last position of a string_view.
2722 * @param __svt The object convertible to string_view to locate.
2723 * @param __pos Index of character to search back from (default end).
2724 * @return Index of start of last occurrence.
2725 */
2726 template<typename _Tp>
2727 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2728 _If_sv<_Tp, size_type>
2729 rfind(const _Tp& __svt, size_type __pos = npos) const
2730 noexcept(is_same<_Tp, __sv_type>::value)
2731 {
2732 __sv_type __sv = __svt;
2733 return this->rfind(__sv.data(), __pos, __sv.size());
2734 }
2735#endif // C++17
2736
2737 /**
2738 * @brief Find last position of a C substring.
2739 * @param __s C string to locate.
2740 * @param __pos Index of character to search back from.
2741 * @param __n Number of characters from s to search for.
2742 * @return Index of start of last occurrence.
2743 *
2744 * Starting from @a __pos, searches backward for the first @a
2745 * __n characters in @a __s within this string. If found,
2746 * returns the index where it begins. If not found, returns
2747 * npos.
2748 */
2749 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2750 size_type
2751 rfind(const _CharT* __s, size_type __pos, size_type __n) const
2752 _GLIBCXX_NOEXCEPTnoexcept;
2753
2754 /**
2755 * @brief Find last position of a C string.
2756 * @param __s C string to locate.
2757 * @param __pos Index of character to start search at (default end).
2758 * @return Index of start of last occurrence.
2759 *
2760 * Starting from @a __pos, searches backward for the value of
2761 * @a __s within this string. If found, returns the index
2762 * where it begins. If not found, returns npos.
2763 */
2764 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2765 size_type
2766 rfind(const _CharT* __s, size_type __pos = npos) const
2767 {
2768 __glibcxx_requires_string(__s);
2769 return this->rfind(__s, __pos, traits_type::length(__s));
2770 }
2771
2772 /**
2773 * @brief Find last position of a character.
2774 * @param __c Character to locate.
2775 * @param __pos Index of character to search back from (default end).
2776 * @return Index of last occurrence.
2777 *
2778 * Starting from @a __pos, searches backward for @a __c within
2779 * this string. If found, returns the index where it was
2780 * found. If not found, returns npos.
2781 */
2782 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2783 size_type
2784 rfind(_CharT __c, size_type __pos = npos) const _GLIBCXX_NOEXCEPTnoexcept;
2785
2786 /**
2787 * @brief Find position of a character of string.
2788 * @param __str String containing characters to locate.
2789 * @param __pos Index of character to search from (default 0).
2790 * @return Index of first occurrence.
2791 *
2792 * Starting from @a __pos, searches forward for one of the
2793 * characters of @a __str within this string. If found,
2794 * returns the index where it was found. If not found, returns
2795 * npos.
2796 */
2797 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2798 size_type
2799 find_first_of(const basic_string& __str, size_type __pos = 0) const
2800 _GLIBCXX_NOEXCEPTnoexcept
2801 { return this->find_first_of(__str.data(), __pos, __str.size()); }
2802
2803#if __cplusplus202002L >= 201703L
2804 /**
2805 * @brief Find position of a character of a string_view.
2806 * @param __svt An object convertible to string_view containing
2807 * characters to locate.
2808 * @param __pos Index of character to search from (default 0).
2809 * @return Index of first occurrence.
2810 */
2811 template<typename _Tp>
2812 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2813 _If_sv<_Tp, size_type>
2814 find_first_of(const _Tp& __svt, size_type __pos = 0) const
2815 noexcept(is_same<_Tp, __sv_type>::value)
2816 {
2817 __sv_type __sv = __svt;
2818 return this->find_first_of(__sv.data(), __pos, __sv.size());
2819 }
2820#endif // C++17
2821
2822 /**
2823 * @brief Find position of a character of C substring.
2824 * @param __s String containing characters to locate.
2825 * @param __pos Index of character to search from.
2826 * @param __n Number of characters from s to search for.
2827 * @return Index of first occurrence.
2828 *
2829 * Starting from @a __pos, searches forward for one of the
2830 * first @a __n characters of @a __s within this string. If
2831 * found, returns the index where it was found. If not found,
2832 * returns npos.
2833 */
2834 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2835 size_type
2836 find_first_of(const _CharT* __s, size_type __pos, size_type __n) const
2837 _GLIBCXX_NOEXCEPTnoexcept;
2838
2839 /**
2840 * @brief Find position of a character of C string.
2841 * @param __s String containing characters to locate.
2842 * @param __pos Index of character to search from (default 0).
2843 * @return Index of first occurrence.
2844 *
2845 * Starting from @a __pos, searches forward for one of the
2846 * characters of @a __s within this string. If found, returns
2847 * the index where it was found. If not found, returns npos.
2848 */
2849 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2850 size_type
2851 find_first_of(const _CharT* __s, size_type __pos = 0) const
2852 _GLIBCXX_NOEXCEPTnoexcept
2853 {
2854 __glibcxx_requires_string(__s);
2855 return this->find_first_of(__s, __pos, traits_type::length(__s));
2856 }
2857
2858 /**
2859 * @brief Find position of a character.
2860 * @param __c Character to locate.
2861 * @param __pos Index of character to search from (default 0).
2862 * @return Index of first occurrence.
2863 *
2864 * Starting from @a __pos, searches forward for the character
2865 * @a __c within this string. If found, returns the index
2866 * where it was found. If not found, returns npos.
2867 *
2868 * Note: equivalent to find(__c, __pos).
2869 */
2870 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2871 size_type
2872 find_first_of(_CharT __c, size_type __pos = 0) const _GLIBCXX_NOEXCEPTnoexcept
2873 { return this->find(__c, __pos); }
2874
2875 /**
2876 * @brief Find last position of a character of string.
2877 * @param __str String containing characters to locate.
2878 * @param __pos Index of character to search back from (default end).
2879 * @return Index of last occurrence.
2880 *
2881 * Starting from @a __pos, searches backward for one of the
2882 * characters of @a __str within this string. If found,
2883 * returns the index where it was found. If not found, returns
2884 * npos.
2885 */
2886 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2887 size_type
2888 find_last_of(const basic_string& __str, size_type __pos = npos) const
2889 _GLIBCXX_NOEXCEPTnoexcept
2890 { return this->find_last_of(__str.data(), __pos, __str.size()); }
2891
2892#if __cplusplus202002L >= 201703L
2893 /**
2894 * @brief Find last position of a character of string.
2895 * @param __svt An object convertible to string_view containing
2896 * characters to locate.
2897 * @param __pos Index of character to search back from (default end).
2898 * @return Index of last occurrence.
2899 */
2900 template<typename _Tp>
2901 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2902 _If_sv<_Tp, size_type>
2903 find_last_of(const _Tp& __svt, size_type __pos = npos) const
2904 noexcept(is_same<_Tp, __sv_type>::value)
2905 {
2906 __sv_type __sv = __svt;
2907 return this->find_last_of(__sv.data(), __pos, __sv.size());
2908 }
2909#endif // C++17
2910
2911 /**
2912 * @brief Find last position of a character of C substring.
2913 * @param __s C string containing characters to locate.
2914 * @param __pos Index of character to search back from.
2915 * @param __n Number of characters from s to search for.
2916 * @return Index of last occurrence.
2917 *
2918 * Starting from @a __pos, searches backward for one of the
2919 * first @a __n characters of @a __s within this string. If
2920 * found, returns the index where it was found. If not found,
2921 * returns npos.
2922 */
2923 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2924 size_type
2925 find_last_of(const _CharT* __s, size_type __pos, size_type __n) const
2926 _GLIBCXX_NOEXCEPTnoexcept;
2927
2928 /**
2929 * @brief Find last position of a character of C string.
2930 * @param __s C string containing characters to locate.
2931 * @param __pos Index of character to search back from (default end).
2932 * @return Index of last occurrence.
2933 *
2934 * Starting from @a __pos, searches backward for one of the
2935 * characters of @a __s within this string. If found, returns
2936 * the index where it was found. If not found, returns npos.
2937 */
2938 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2939 size_type
2940 find_last_of(const _CharT* __s, size_type __pos = npos) const
2941 _GLIBCXX_NOEXCEPTnoexcept
2942 {
2943 __glibcxx_requires_string(__s);
2944 return this->find_last_of(__s, __pos, traits_type::length(__s));
2945 }
2946
2947 /**
2948 * @brief Find last position of a character.
2949 * @param __c Character to locate.
2950 * @param __pos Index of character to search back from (default end).
2951 * @return Index of last occurrence.
2952 *
2953 * Starting from @a __pos, searches backward for @a __c within
2954 * this string. If found, returns the index where it was
2955 * found. If not found, returns npos.
2956 *
2957 * Note: equivalent to rfind(__c, __pos).
2958 */
2959 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2960 size_type
2961 find_last_of(_CharT __c, size_type __pos = npos) const _GLIBCXX_NOEXCEPTnoexcept
2962 { return this->rfind(__c, __pos); }
2963
2964 /**
2965 * @brief Find position of a character not in string.
2966 * @param __str String containing characters to avoid.
2967 * @param __pos Index of character to search from (default 0).
2968 * @return Index of first occurrence.
2969 *
2970 * Starting from @a __pos, searches forward for a character not contained
2971 * in @a __str within this string. If found, returns the index where it
2972 * was found. If not found, returns npos.
2973 */
2974 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2975 size_type
2976 find_first_not_of(const basic_string& __str, size_type __pos = 0) const
2977 _GLIBCXX_NOEXCEPTnoexcept
2978 { return this->find_first_not_of(__str.data(), __pos, __str.size()); }
2979
2980#if __cplusplus202002L >= 201703L
2981 /**
2982 * @brief Find position of a character not in a string_view.
2983 * @param __svt A object convertible to string_view containing
2984 * characters to avoid.
2985 * @param __pos Index of character to search from (default 0).
2986 * @return Index of first occurrence.
2987 */
2988 template<typename _Tp>
2989 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
2990 _If_sv<_Tp, size_type>
2991 find_first_not_of(const _Tp& __svt, size_type __pos = 0) const
2992 noexcept(is_same<_Tp, __sv_type>::value)
2993 {
2994 __sv_type __sv = __svt;
2995 return this->find_first_not_of(__sv.data(), __pos, __sv.size());
2996 }
2997#endif // C++17
2998
2999 /**
3000 * @brief Find position of a character not in C substring.
3001 * @param __s C string containing characters to avoid.
3002 * @param __pos Index of character to search from.
3003 * @param __n Number of characters from __s to consider.
3004 * @return Index of first occurrence.
3005 *
3006 * Starting from @a __pos, searches forward for a character not
3007 * contained in the first @a __n characters of @a __s within
3008 * this string. If found, returns the index where it was
3009 * found. If not found, returns npos.
3010 */
3011 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3012 size_type
3013 find_first_not_of(const _CharT* __s, size_type __pos,
3014 size_type __n) const _GLIBCXX_NOEXCEPTnoexcept;
3015
3016 /**
3017 * @brief Find position of a character not in C string.
3018 * @param __s C string containing characters to avoid.
3019 * @param __pos Index of character to search from (default 0).
3020 * @return Index of first occurrence.
3021 *
3022 * Starting from @a __pos, searches forward for a character not
3023 * contained in @a __s within this string. If found, returns
3024 * the index where it was found. If not found, returns npos.
3025 */
3026 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3027 size_type
3028 find_first_not_of(const _CharT* __s, size_type __pos = 0) const
3029 _GLIBCXX_NOEXCEPTnoexcept
3030 {
3031 __glibcxx_requires_string(__s);
3032 return this->find_first_not_of(__s, __pos, traits_type::length(__s));
3033 }
3034
3035 /**
3036 * @brief Find position of a different character.
3037 * @param __c Character to avoid.
3038 * @param __pos Index of character to search from (default 0).
3039 * @return Index of first occurrence.
3040 *
3041 * Starting from @a __pos, searches forward for a character
3042 * other than @a __c within this string. If found, returns the
3043 * index where it was found. If not found, returns npos.
3044 */
3045 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3046 size_type
3047 find_first_not_of(_CharT __c, size_type __pos = 0) const
3048 _GLIBCXX_NOEXCEPTnoexcept;
3049
3050 /**
3051 * @brief Find last position of a character not in string.
3052 * @param __str String containing characters to avoid.
3053 * @param __pos Index of character to search back from (default end).
3054 * @return Index of last occurrence.
3055 *
3056 * Starting from @a __pos, searches backward for a character
3057 * not contained in @a __str within this string. If found,
3058 * returns the index where it was found. If not found, returns
3059 * npos.
3060 */
3061 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3062 size_type
3063 find_last_not_of(const basic_string& __str, size_type __pos = npos) const
3064 _GLIBCXX_NOEXCEPTnoexcept
3065 { return this->find_last_not_of(__str.data(), __pos, __str.size()); }
3066
3067#if __cplusplus202002L >= 201703L
3068 /**
3069 * @brief Find last position of a character not in a string_view.
3070 * @param __svt An object convertible to string_view containing
3071 * characters to avoid.
3072 * @param __pos Index of character to search back from (default end).
3073 * @return Index of last occurrence.
3074 */
3075 template<typename _Tp>
3076 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3077 _If_sv<_Tp, size_type>
3078 find_last_not_of(const _Tp& __svt, size_type __pos = npos) const
3079 noexcept(is_same<_Tp, __sv_type>::value)
3080 {
3081 __sv_type __sv = __svt;
3082 return this->find_last_not_of(__sv.data(), __pos, __sv.size());
3083 }
3084#endif // C++17
3085
3086 /**
3087 * @brief Find last position of a character not in C substring.
3088 * @param __s C string containing characters to avoid.
3089 * @param __pos Index of character to search back from.
3090 * @param __n Number of characters from s to consider.
3091 * @return Index of last occurrence.
3092 *
3093 * Starting from @a __pos, searches backward for a character not
3094 * contained in the first @a __n characters of @a __s within this string.
3095 * If found, returns the index where it was found. If not found,
3096 * returns npos.
3097 */
3098 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3099 size_type
3100 find_last_not_of(const _CharT* __s, size_type __pos,
3101 size_type __n) const _GLIBCXX_NOEXCEPTnoexcept;
3102 /**
3103 * @brief Find last position of a character not in C string.
3104 * @param __s C string containing characters to avoid.
3105 * @param __pos Index of character to search back from (default end).
3106 * @return Index of last occurrence.
3107 *
3108 * Starting from @a __pos, searches backward for a character
3109 * not contained in @a __s within this string. If found,
3110 * returns the index where it was found. If not found, returns
3111 * npos.
3112 */
3113 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3114 size_type
3115 find_last_not_of(const _CharT* __s, size_type __pos = npos) const
3116 _GLIBCXX_NOEXCEPTnoexcept
3117 {
3118 __glibcxx_requires_string(__s);
3119 return this->find_last_not_of(__s, __pos, traits_type::length(__s));
3120 }
3121
3122 /**
3123 * @brief Find last position of a different character.
3124 * @param __c Character to avoid.
3125 * @param __pos Index of character to search back from (default end).
3126 * @return Index of last occurrence.
3127 *
3128 * Starting from @a __pos, searches backward for a character other than
3129 * @a __c within this string. If found, returns the index where it was
3130 * found. If not found, returns npos.
3131 */
3132 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3133 size_type
3134 find_last_not_of(_CharT __c, size_type __pos = npos) const
3135 _GLIBCXX_NOEXCEPTnoexcept;
3136
3137 /**
3138 * @brief Get a substring.
3139 * @param __pos Index of first character (default 0).
3140 * @param __n Number of characters in substring (default remainder).
3141 * @return The new string.
3142 * @throw std::out_of_range If __pos > size().
3143 *
3144 * Construct and return a new string using the @a __n
3145 * characters starting at @a __pos. If the string is too
3146 * short, use the remainder of the characters. If @a __pos is
3147 * beyond the end of the string, out_of_range is thrown.
3148 */
3149 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3150 basic_string
3151 substr(size_type __pos = 0, size_type __n = npos) const
3152 { return basic_string(*this,
3153 _M_check(__pos, "basic_string::substr"), __n); }
3154
3155 /**
3156 * @brief Compare to a string.
3157 * @param __str String to compare against.
3158 * @return Integer < 0, 0, or > 0.
3159 *
3160 * Returns an integer < 0 if this string is ordered before @a
3161 * __str, 0 if their values are equivalent, or > 0 if this
3162 * string is ordered after @a __str. Determines the effective
3163 * length rlen of the strings to compare as the smallest of
3164 * size() and str.size(). The function then compares the two
3165 * strings by calling traits::compare(data(), str.data(),rlen).
3166 * If the result of the comparison is nonzero returns it,
3167 * otherwise the shorter one is ordered first.
3168 */
3169 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3170 int
3171 compare(const basic_string& __str) const
3172 {
3173 const size_type __size = this->size();
3174 const size_type __osize = __str.size();
3175 const size_type __len = std::min(__size, __osize);
3176
3177 int __r = traits_type::compare(_M_data(), __str.data(), __len);
3178 if (!__r)
3179 __r = _S_compare(__size, __osize);
3180 return __r;
3181 }
3182
3183#if __cplusplus202002L >= 201703L
3184 /**
3185 * @brief Compare to a string_view.
3186 * @param __svt An object convertible to string_view to compare against.
3187 * @return Integer < 0, 0, or > 0.
3188 */
3189 template<typename _Tp>
3190 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3191 _If_sv<_Tp, int>
3192 compare(const _Tp& __svt) const
3193 noexcept(is_same<_Tp, __sv_type>::value)
3194 {
3195 __sv_type __sv = __svt;
3196 const size_type __size = this->size();
3197 const size_type __osize = __sv.size();
3198 const size_type __len = std::min(__size, __osize);
3199
3200 int __r = traits_type::compare(_M_data(), __sv.data(), __len);
3201 if (!__r)
3202 __r = _S_compare(__size, __osize);
3203 return __r;
3204 }
3205
3206 /**
3207 * @brief Compare to a string_view.
3208 * @param __pos A position in the string to start comparing from.
3209 * @param __n The number of characters to compare.
3210 * @param __svt An object convertible to string_view to compare
3211 * against.
3212 * @return Integer < 0, 0, or > 0.
3213 */
3214 template<typename _Tp>
3215 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3216 _If_sv<_Tp, int>
3217 compare(size_type __pos, size_type __n, const _Tp& __svt) const
3218 noexcept(is_same<_Tp, __sv_type>::value)
3219 {
3220 __sv_type __sv = __svt;
3221 return __sv_type(*this).substr(__pos, __n).compare(__sv);
3222 }
3223
3224 /**
3225 * @brief Compare to a string_view.
3226 * @param __pos1 A position in the string to start comparing from.
3227 * @param __n1 The number of characters to compare.
3228 * @param __svt An object convertible to string_view to compare
3229 * against.
3230 * @param __pos2 A position in the string_view to start comparing from.
3231 * @param __n2 The number of characters to compare.
3232 * @return Integer < 0, 0, or > 0.
3233 */
3234 template<typename _Tp>
3235 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3236 _If_sv<_Tp, int>
3237 compare(size_type __pos1, size_type __n1, const _Tp& __svt,
3238 size_type __pos2, size_type __n2 = npos) const
3239 noexcept(is_same<_Tp, __sv_type>::value)
3240 {
3241 __sv_type __sv = __svt;
3242 return __sv_type(*this)
3243 .substr(__pos1, __n1).compare(__sv.substr(__pos2, __n2));
3244 }
3245#endif // C++17
3246
3247 /**
3248 * @brief Compare substring to a string.
3249 * @param __pos Index of first character of substring.
3250 * @param __n Number of characters in substring.
3251 * @param __str String to compare against.
3252 * @return Integer < 0, 0, or > 0.
3253 *
3254 * Form the substring of this string from the @a __n characters
3255 * starting at @a __pos. Returns an integer < 0 if the
3256 * substring is ordered before @a __str, 0 if their values are
3257 * equivalent, or > 0 if the substring is ordered after @a
3258 * __str. Determines the effective length rlen of the strings
3259 * to compare as the smallest of the length of the substring
3260 * and @a __str.size(). The function then compares the two
3261 * strings by calling
3262 * traits::compare(substring.data(),str.data(),rlen). If the
3263 * result of the comparison is nonzero returns it, otherwise
3264 * the shorter one is ordered first.
3265 */
3266 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3267 int
3268 compare(size_type __pos, size_type __n, const basic_string& __str) const
3269 {
3270 _M_check(__pos, "basic_string::compare");
3271 __n = _M_limit(__pos, __n);
3272 const size_type __osize = __str.size();
3273 const size_type __len = std::min(__n, __osize);
3274 int __r = traits_type::compare(_M_data() + __pos, __str.data(), __len);
3275 if (!__r)
3276 __r = _S_compare(__n, __osize);
3277 return __r;
3278 }
3279
3280 /**
3281 * @brief Compare substring to a substring.
3282 * @param __pos1 Index of first character of substring.
3283 * @param __n1 Number of characters in substring.
3284 * @param __str String to compare against.
3285 * @param __pos2 Index of first character of substring of str.
3286 * @param __n2 Number of characters in substring of str.
3287 * @return Integer < 0, 0, or > 0.
3288 *
3289 * Form the substring of this string from the @a __n1
3290 * characters starting at @a __pos1. Form the substring of @a
3291 * __str from the @a __n2 characters starting at @a __pos2.
3292 * Returns an integer < 0 if this substring is ordered before
3293 * the substring of @a __str, 0 if their values are equivalent,
3294 * or > 0 if this substring is ordered after the substring of
3295 * @a __str. Determines the effective length rlen of the
3296 * strings to compare as the smallest of the lengths of the
3297 * substrings. The function then compares the two strings by
3298 * calling
3299 * traits::compare(substring.data(),str.substr(pos2,n2).data(),rlen).
3300 * If the result of the comparison is nonzero returns it,
3301 * otherwise the shorter one is ordered first.
3302 */
3303 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3304 int
3305 compare(size_type __pos1, size_type __n1, const basic_string& __str,
3306 size_type __pos2, size_type __n2 = npos) const
3307 {
3308 _M_check(__pos1, "basic_string::compare");
3309 __str._M_check(__pos2, "basic_string::compare");
3310 __n1 = _M_limit(__pos1, __n1);
3311 __n2 = __str._M_limit(__pos2, __n2);
3312 const size_type __len = std::min(__n1, __n2);
3313 int __r = traits_type::compare(_M_data() + __pos1,
3314 __str.data() + __pos2, __len);
3315 if (!__r)
3316 __r = _S_compare(__n1, __n2);
3317 return __r;
3318 }
3319
3320 /**
3321 * @brief Compare to a C string.
3322 * @param __s C string to compare against.
3323 * @return Integer < 0, 0, or > 0.
3324 *
3325 * Returns an integer < 0 if this string is ordered before @a __s, 0 if
3326 * their values are equivalent, or > 0 if this string is ordered after
3327 * @a __s. Determines the effective length rlen of the strings to
3328 * compare as the smallest of size() and the length of a string
3329 * constructed from @a __s. The function then compares the two strings
3330 * by calling traits::compare(data(),s,rlen). If the result of the
3331 * comparison is nonzero returns it, otherwise the shorter one is
3332 * ordered first.
3333 */
3334 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3335 int
3336 compare(const _CharT* __s) const _GLIBCXX_NOEXCEPTnoexcept
3337 {
3338 __glibcxx_requires_string(__s);
3339 const size_type __size = this->size();
3340 const size_type __osize = traits_type::length(__s);
3341 const size_type __len = std::min(__size, __osize);
3342 int __r = traits_type::compare(_M_data(), __s, __len);
3343 if (!__r)
3344 __r = _S_compare(__size, __osize);
3345 return __r;
3346 }
3347
3348 // _GLIBCXX_RESOLVE_LIB_DEFECTS
3349 // 5 String::compare specification questionable
3350 /**
3351 * @brief Compare substring to a C string.
3352 * @param __pos Index of first character of substring.
3353 * @param __n1 Number of characters in substring.
3354 * @param __s C string to compare against.
3355 * @return Integer < 0, 0, or > 0.
3356 *
3357 * Form the substring of this string from the @a __n1
3358 * characters starting at @a pos. Returns an integer < 0 if
3359 * the substring is ordered before @a __s, 0 if their values
3360 * are equivalent, or > 0 if the substring is ordered after @a
3361 * __s. Determines the effective length rlen of the strings to
3362 * compare as the smallest of the length of the substring and
3363 * the length of a string constructed from @a __s. The
3364 * function then compares the two string by calling
3365 * traits::compare(substring.data(),__s,rlen). If the result of
3366 * the comparison is nonzero returns it, otherwise the shorter
3367 * one is ordered first.
3368 */
3369 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3370 int
3371 compare(size_type __pos, size_type __n1, const _CharT* __s) const
3372 {
3373 __glibcxx_requires_string(__s);
3374 _M_check(__pos, "basic_string::compare");
3375 __n1 = _M_limit(__pos, __n1);
3376 const size_type __osize = traits_type::length(__s);
3377 const size_type __len = std::min(__n1, __osize);
3378 int __r = traits_type::compare(_M_data() + __pos, __s, __len);
3379 if (!__r)
3380 __r = _S_compare(__n1, __osize);
3381 return __r;
3382 }
3383
3384 /**
3385 * @brief Compare substring against a character %array.
3386 * @param __pos Index of first character of substring.
3387 * @param __n1 Number of characters in substring.
3388 * @param __s character %array to compare against.
3389 * @param __n2 Number of characters of s.
3390 * @return Integer < 0, 0, or > 0.
3391 *
3392 * Form the substring of this string from the @a __n1
3393 * characters starting at @a __pos. Form a string from the
3394 * first @a __n2 characters of @a __s. Returns an integer < 0
3395 * if this substring is ordered before the string from @a __s,
3396 * 0 if their values are equivalent, or > 0 if this substring
3397 * is ordered after the string from @a __s. Determines the
3398 * effective length rlen of the strings to compare as the
3399 * smallest of the length of the substring and @a __n2. The
3400 * function then compares the two strings by calling
3401 * traits::compare(substring.data(),s,rlen). If the result of
3402 * the comparison is nonzero returns it, otherwise the shorter
3403 * one is ordered first.
3404 *
3405 * NB: s must have at least n2 characters, &apos;\\0&apos; has
3406 * no special meaning.
3407 */
3408 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3409 int
3410 compare(size_type __pos, size_type __n1, const _CharT* __s,
3411 size_type __n2) const
3412 {
3413 __glibcxx_requires_string_len(__s, __n2);
3414 _M_check(__pos, "basic_string::compare");
3415 __n1 = _M_limit(__pos, __n1);
3416 const size_type __len = std::min(__n1, __n2);
3417 int __r = traits_type::compare(_M_data() + __pos, __s, __len);
3418 if (!__r)
3419 __r = _S_compare(__n1, __n2);
3420 return __r;
3421 }
3422
3423#if __cplusplus202002L >= 202002L
3424 [[nodiscard]]
3425 constexpr bool
3426 starts_with(basic_string_view<_CharT, _Traits> __x) const noexcept
3427 { return __sv_type(this->data(), this->size()).starts_with(__x); }
3428
3429 [[nodiscard]]
3430 constexpr bool
3431 starts_with(_CharT __x) const noexcept
3432 { return __sv_type(this->data(), this->size()).starts_with(__x); }
3433
3434 [[nodiscard, __gnu__::__nonnull__]]
3435 constexpr bool
3436 starts_with(const _CharT* __x) const noexcept
3437 { return __sv_type(this->data(), this->size()).starts_with(__x); }
3438
3439 [[nodiscard]]
3440 constexpr bool
3441 ends_with(basic_string_view<_CharT, _Traits> __x) const noexcept
3442 { return __sv_type(this->data(), this->size()).ends_with(__x); }
3443
3444 [[nodiscard]]
3445 constexpr bool
3446 ends_with(_CharT __x) const noexcept
3447 { return __sv_type(this->data(), this->size()).ends_with(__x); }
3448
3449 [[nodiscard, __gnu__::__nonnull__]]
3450 constexpr bool
3451 ends_with(const _CharT* __x) const noexcept
3452 { return __sv_type(this->data(), this->size()).ends_with(__x); }
3453#endif // C++20
3454
3455#if __cplusplus202002L > 202002L
3456 [[nodiscard]]
3457 constexpr bool
3458 contains(basic_string_view<_CharT, _Traits> __x) const noexcept
3459 { return __sv_type(this->data(), this->size()).contains(__x); }
3460
3461 [[nodiscard]]
3462 constexpr bool
3463 contains(_CharT __x) const noexcept
3464 { return __sv_type(this->data(), this->size()).contains(__x); }
3465
3466 [[nodiscard, __gnu__::__nonnull__]]
3467 constexpr bool
3468 contains(const _CharT* __x) const noexcept
3469 { return __sv_type(this->data(), this->size()).contains(__x); }
3470#endif // C++23
3471
3472 // Allow basic_stringbuf::__xfer_bufptrs to call _M_length:
3473 template<typename, typename, typename> friend class basic_stringbuf;
3474 };
3475_GLIBCXX_END_NAMESPACE_CXX11}
3476_GLIBCXX_END_NAMESPACE_VERSION
3477} // namespace std
3478#endif // _GLIBCXX_USE_CXX11_ABI
3479
3480namespace std _GLIBCXX_VISIBILITY(default)__attribute__ ((__visibility__ ("default")))
3481{
3482_GLIBCXX_BEGIN_NAMESPACE_VERSION
3483
3484#if __cpp_deduction_guides201703L >= 201606
3485_GLIBCXX_BEGIN_NAMESPACE_CXX11namespace __cxx11 {
3486 template<typename _InputIterator, typename _CharT
3487 = typename iterator_traits<_InputIterator>::value_type,
3488 typename _Allocator = allocator<_CharT>,
3489 typename = _RequireInputIter<_InputIterator>,
3490 typename = _RequireAllocator<_Allocator>>
3491 basic_string(_InputIterator, _InputIterator, _Allocator = _Allocator())
3492 -> basic_string<_CharT, char_traits<_CharT>, _Allocator>;
3493
3494 // _GLIBCXX_RESOLVE_LIB_DEFECTS
3495 // 3075. basic_string needs deduction guides from basic_string_view
3496 template<typename _CharT, typename _Traits,
3497 typename _Allocator = allocator<_CharT>,
3498 typename = _RequireAllocator<_Allocator>>
3499 basic_string(basic_string_view<_CharT, _Traits>, const _Allocator& = _Allocator())
3500 -> basic_string<_CharT, _Traits, _Allocator>;
3501
3502 template<typename _CharT, typename _Traits,
3503 typename _Allocator = allocator<_CharT>,
3504 typename = _RequireAllocator<_Allocator>>
3505 basic_string(basic_string_view<_CharT, _Traits>,
3506 typename basic_string<_CharT, _Traits, _Allocator>::size_type,
3507 typename basic_string<_CharT, _Traits, _Allocator>::size_type,
3508 const _Allocator& = _Allocator())
3509 -> basic_string<_CharT, _Traits, _Allocator>;
3510_GLIBCXX_END_NAMESPACE_CXX11}
3511#endif
3512
3513 template<typename _Str>
3514 _GLIBCXX20_CONSTEXPRconstexpr
3515 inline _Str
3516 __str_concat(typename _Str::value_type const* __lhs,
3517 typename _Str::size_type __lhs_len,
3518 typename _Str::value_type const* __rhs,
3519 typename _Str::size_type __rhs_len,
3520 typename _Str::allocator_type const& __a)
3521 {
3522 typedef typename _Str::allocator_type allocator_type;
3523 typedef __gnu_cxx::__alloc_traits<allocator_type> _Alloc_traits;
3524 _Str __str(_Alloc_traits::_S_select_on_copy(__a));
3525 __str.reserve(__lhs_len + __rhs_len);
3526 __str.append(__lhs, __lhs_len);
3527 __str.append(__rhs, __rhs_len);
3528 return __str;
3529 }
3530
3531 // operator+
3532 /**
3533 * @brief Concatenate two strings.
3534 * @param __lhs First string.
3535 * @param __rhs Last string.
3536 * @return New string with value of @a __lhs followed by @a __rhs.
3537 */
3538 template<typename _CharT, typename _Traits, typename _Alloc>
3539 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3540 inline basic_string<_CharT, _Traits, _Alloc>
3541 operator+(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3542 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3543 {
3544 typedef basic_string<_CharT, _Traits, _Alloc> _Str;
3545 return std::__str_concat<_Str>(__lhs.c_str(), __lhs.size(),
3546 __rhs.c_str(), __rhs.size(),
3547 __lhs.get_allocator());
3548 }
3549
3550 /**
3551 * @brief Concatenate C string and string.
3552 * @param __lhs First string.
3553 * @param __rhs Last string.
3554 * @return New string with value of @a __lhs followed by @a __rhs.
3555 */
3556 template<typename _CharT, typename _Traits, typename _Alloc>
3557 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3558 inline basic_string<_CharT,_Traits,_Alloc>
3559 operator+(const _CharT* __lhs,
3560 const basic_string<_CharT,_Traits,_Alloc>& __rhs)
3561 {
3562 __glibcxx_requires_string(__lhs);
3563 typedef basic_string<_CharT, _Traits, _Alloc> _Str;
3564 return std::__str_concat<_Str>(__lhs, _Traits::length(__lhs),
3565 __rhs.c_str(), __rhs.size(),
3566 __rhs.get_allocator());
3567 }
3568
3569 /**
3570 * @brief Concatenate character and string.
3571 * @param __lhs First string.
3572 * @param __rhs Last string.
3573 * @return New string with @a __lhs followed by @a __rhs.
3574 */
3575 template<typename _CharT, typename _Traits, typename _Alloc>
3576 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3577 inline basic_string<_CharT,_Traits,_Alloc>
3578 operator+(_CharT __lhs, const basic_string<_CharT,_Traits,_Alloc>& __rhs)
3579 {
3580 typedef basic_string<_CharT, _Traits, _Alloc> _Str;
3581 return std::__str_concat<_Str>(__builtin_addressof(__lhs), 1,
3582 __rhs.c_str(), __rhs.size(),
3583 __rhs.get_allocator());
3584 }
3585
3586 /**
3587 * @brief Concatenate string and C string.
3588 * @param __lhs First string.
3589 * @param __rhs Last string.
3590 * @return New string with @a __lhs followed by @a __rhs.
3591 */
3592 template<typename _CharT, typename _Traits, typename _Alloc>
3593 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3594 inline basic_string<_CharT, _Traits, _Alloc>
3595 operator+(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3596 const _CharT* __rhs)
3597 {
3598 __glibcxx_requires_string(__rhs);
3599 typedef basic_string<_CharT, _Traits, _Alloc> _Str;
3600 return std::__str_concat<_Str>(__lhs.c_str(), __lhs.size(),
3601 __rhs, _Traits::length(__rhs),
3602 __lhs.get_allocator());
3603 }
3604 /**
3605 * @brief Concatenate string and character.
3606 * @param __lhs First string.
3607 * @param __rhs Last string.
3608 * @return New string with @a __lhs followed by @a __rhs.
3609 */
3610 template<typename _CharT, typename _Traits, typename _Alloc>
3611 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3612 inline basic_string<_CharT, _Traits, _Alloc>
3613 operator+(const basic_string<_CharT, _Traits, _Alloc>& __lhs, _CharT __rhs)
3614 {
3615 typedef basic_string<_CharT, _Traits, _Alloc> _Str;
3616 return std::__str_concat<_Str>(__lhs.c_str(), __lhs.size(),
3617 __builtin_addressof(__rhs), 1,
3618 __lhs.get_allocator());
3619 }
3620
3621#if __cplusplus202002L >= 201103L
3622 template<typename _CharT, typename _Traits, typename _Alloc>
3623 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3624 inline basic_string<_CharT, _Traits, _Alloc>
3625 operator+(basic_string<_CharT, _Traits, _Alloc>&& __lhs,
3626 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3627 { return std::move(__lhs.append(__rhs)); }
3628
3629 template<typename _CharT, typename _Traits, typename _Alloc>
3630 _GLIBCXX20_CONSTEXPRconstexpr
3631 inline basic_string<_CharT, _Traits, _Alloc>
3632 operator+(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3633 basic_string<_CharT, _Traits, _Alloc>&& __rhs)
3634 { return std::move(__rhs.insert(0, __lhs)); }
3635
3636 template<typename _CharT, typename _Traits, typename _Alloc>
3637 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3638 inline basic_string<_CharT, _Traits, _Alloc>
3639 operator+(basic_string<_CharT, _Traits, _Alloc>&& __lhs,
3640 basic_string<_CharT, _Traits, _Alloc>&& __rhs)
3641 {
3642#if _GLIBCXX_USE_CXX11_ABI1
3643 using _Alloc_traits = allocator_traits<_Alloc>;
3644 bool __use_rhs = false;
3645 if _GLIBCXX17_CONSTEXPRconstexpr (typename _Alloc_traits::is_always_equal{})
3646 __use_rhs = true;
3647 else if (__lhs.get_allocator() == __rhs.get_allocator())
3648 __use_rhs = true;
3649 if (__use_rhs)
3650#endif
3651 {
3652 const auto __size = __lhs.size() + __rhs.size();
3653 if (__size > __lhs.capacity() && __size <= __rhs.capacity())
3654 return std::move(__rhs.insert(0, __lhs));
3655 }
3656 return std::move(__lhs.append(__rhs));
3657 }
3658
3659 template<typename _CharT, typename _Traits, typename _Alloc>
3660 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3661 inline basic_string<_CharT, _Traits, _Alloc>
3662 operator+(const _CharT* __lhs,
3663 basic_string<_CharT, _Traits, _Alloc>&& __rhs)
3664 { return std::move(__rhs.insert(0, __lhs)); }
3665
3666 template<typename _CharT, typename _Traits, typename _Alloc>
3667 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3668 inline basic_string<_CharT, _Traits, _Alloc>
3669 operator+(_CharT __lhs,
3670 basic_string<_CharT, _Traits, _Alloc>&& __rhs)
3671 { return std::move(__rhs.insert(0, 1, __lhs)); }
3672
3673 template<typename _CharT, typename _Traits, typename _Alloc>
3674 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3675 inline basic_string<_CharT, _Traits, _Alloc>
3676 operator+(basic_string<_CharT, _Traits, _Alloc>&& __lhs,
3677 const _CharT* __rhs)
3678 { return std::move(__lhs.append(__rhs)); }
3679
3680 template<typename _CharT, typename _Traits, typename _Alloc>
3681 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3682 inline basic_string<_CharT, _Traits, _Alloc>
3683 operator+(basic_string<_CharT, _Traits, _Alloc>&& __lhs,
3684 _CharT __rhs)
3685 { return std::move(__lhs.append(1, __rhs)); }
3686#endif
3687
3688 // operator ==
3689 /**
3690 * @brief Test equivalence of two strings.
3691 * @param __lhs First string.
3692 * @param __rhs Second string.
3693 * @return True if @a __lhs.compare(@a __rhs) == 0. False otherwise.
3694 */
3695 template<typename _CharT, typename _Traits, typename _Alloc>
3696 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3697 inline bool
3698 operator==(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3699 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3700 _GLIBCXX_NOEXCEPTnoexcept
3701 {
3702 return __lhs.size() == __rhs.size()
3703 && !_Traits::compare(__lhs.data(), __rhs.data(), __lhs.size());
3704 }
3705
3706 /**
3707 * @brief Test equivalence of string and C string.
3708 * @param __lhs String.
3709 * @param __rhs C string.
3710 * @return True if @a __lhs.compare(@a __rhs) == 0. False otherwise.
3711 */
3712 template<typename _CharT, typename _Traits, typename _Alloc>
3713 _GLIBCXX_NODISCARD[[__nodiscard__]] _GLIBCXX20_CONSTEXPRconstexpr
3714 inline bool
3715 operator==(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3716 const _CharT* __rhs)
3717 {
3718 return __lhs.size() == _Traits::length(__rhs)
3719 && !_Traits::compare(__lhs.data(), __rhs, __lhs.size());
3720 }
3721
3722#if __cpp_lib_three_way_comparison201907L
3723 /**
3724 * @brief Three-way comparison of a string and a C string.
3725 * @param __lhs A string.
3726 * @param __rhs A null-terminated string.
3727 * @return A value indicating whether `__lhs` is less than, equal to,
3728 * greater than, or incomparable with `__rhs`.
3729 */
3730 template<typename _CharT, typename _Traits, typename _Alloc>
3731 [[nodiscard]]
3732 constexpr auto
3733 operator<=>(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3734 const basic_string<_CharT, _Traits, _Alloc>& __rhs) noexcept
3735 -> decltype(__detail::__char_traits_cmp_cat<_Traits>(0))
3736 { return __detail::__char_traits_cmp_cat<_Traits>(__lhs.compare(__rhs)); }
3737
3738 /**
3739 * @brief Three-way comparison of a string and a C string.
3740 * @param __lhs A string.
3741 * @param __rhs A null-terminated string.
3742 * @return A value indicating whether `__lhs` is less than, equal to,
3743 * greater than, or incomparable with `__rhs`.
3744 */
3745 template<typename _CharT, typename _Traits, typename _Alloc>
3746 [[nodiscard]]
3747 constexpr auto
3748 operator<=>(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3749 const _CharT* __rhs) noexcept
3750 -> decltype(__detail::__char_traits_cmp_cat<_Traits>(0))
3751 { return __detail::__char_traits_cmp_cat<_Traits>(__lhs.compare(__rhs)); }
3752#else
3753 /**
3754 * @brief Test equivalence of C string and string.
3755 * @param __lhs C string.
3756 * @param __rhs String.
3757 * @return True if @a __rhs.compare(@a __lhs) == 0. False otherwise.
3758 */
3759 template<typename _CharT, typename _Traits, typename _Alloc>
3760 _GLIBCXX_NODISCARD[[__nodiscard__]]
3761 inline bool
3762 operator==(const _CharT* __lhs,
3763 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3764 { return __rhs == __lhs; }
3765
3766 // operator !=
3767 /**
3768 * @brief Test difference of two strings.
3769 * @param __lhs First string.
3770 * @param __rhs Second string.
3771 * @return True if @a __lhs.compare(@a __rhs) != 0. False otherwise.
3772 */
3773 template<typename _CharT, typename _Traits, typename _Alloc>
3774 _GLIBCXX_NODISCARD[[__nodiscard__]]
3775 inline bool
3776 operator!=(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3777 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3778 _GLIBCXX_NOEXCEPTnoexcept
3779 { return !(__lhs == __rhs); }
3780
3781 /**
3782 * @brief Test difference of C string and string.
3783 * @param __lhs C string.
3784 * @param __rhs String.
3785 * @return True if @a __rhs.compare(@a __lhs) != 0. False otherwise.
3786 */
3787 template<typename _CharT, typename _Traits, typename _Alloc>
3788 _GLIBCXX_NODISCARD[[__nodiscard__]]
3789 inline bool
3790 operator!=(const _CharT* __lhs,
3791 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3792 { return !(__rhs == __lhs); }
3793
3794 /**
3795 * @brief Test difference of string and C string.
3796 * @param __lhs String.
3797 * @param __rhs C string.
3798 * @return True if @a __lhs.compare(@a __rhs) != 0. False otherwise.
3799 */
3800 template<typename _CharT, typename _Traits, typename _Alloc>
3801 _GLIBCXX_NODISCARD[[__nodiscard__]]
3802 inline bool
3803 operator!=(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3804 const _CharT* __rhs)
3805 { return !(__lhs == __rhs); }
3806
3807 // operator <
3808 /**
3809 * @brief Test if string precedes string.
3810 * @param __lhs First string.
3811 * @param __rhs Second string.
3812 * @return True if @a __lhs precedes @a __rhs. False otherwise.
3813 */
3814 template<typename _CharT, typename _Traits, typename _Alloc>
3815 _GLIBCXX_NODISCARD[[__nodiscard__]]
3816 inline bool
3817 operator<(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3818 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3819 _GLIBCXX_NOEXCEPTnoexcept
3820 { return __lhs.compare(__rhs) < 0; }
3821
3822 /**
3823 * @brief Test if string precedes C string.
3824 * @param __lhs String.
3825 * @param __rhs C string.
3826 * @return True if @a __lhs precedes @a __rhs. False otherwise.
3827 */
3828 template<typename _CharT, typename _Traits, typename _Alloc>
3829 _GLIBCXX_NODISCARD[[__nodiscard__]]
3830 inline bool
3831 operator<(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3832 const _CharT* __rhs)
3833 { return __lhs.compare(__rhs) < 0; }
3834
3835 /**
3836 * @brief Test if C string precedes string.
3837 * @param __lhs C string.
3838 * @param __rhs String.
3839 * @return True if @a __lhs precedes @a __rhs. False otherwise.
3840 */
3841 template<typename _CharT, typename _Traits, typename _Alloc>
3842 _GLIBCXX_NODISCARD[[__nodiscard__]]
3843 inline bool
3844 operator<(const _CharT* __lhs,
3845 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3846 { return __rhs.compare(__lhs) > 0; }
3847
3848 // operator >
3849 /**
3850 * @brief Test if string follows string.
3851 * @param __lhs First string.
3852 * @param __rhs Second string.
3853 * @return True if @a __lhs follows @a __rhs. False otherwise.
3854 */
3855 template<typename _CharT, typename _Traits, typename _Alloc>
3856 _GLIBCXX_NODISCARD[[__nodiscard__]]
3857 inline bool
3858 operator>(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3859 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3860 _GLIBCXX_NOEXCEPTnoexcept
3861 { return __lhs.compare(__rhs) > 0; }
3862
3863 /**
3864 * @brief Test if string follows C string.
3865 * @param __lhs String.
3866 * @param __rhs C string.
3867 * @return True if @a __lhs follows @a __rhs. False otherwise.
3868 */
3869 template<typename _CharT, typename _Traits, typename _Alloc>
3870 _GLIBCXX_NODISCARD[[__nodiscard__]]
3871 inline bool
3872 operator>(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3873 const _CharT* __rhs)
3874 { return __lhs.compare(__rhs) > 0; }
3875
3876 /**
3877 * @brief Test if C string follows string.
3878 * @param __lhs C string.
3879 * @param __rhs String.
3880 * @return True if @a __lhs follows @a __rhs. False otherwise.
3881 */
3882 template<typename _CharT, typename _Traits, typename _Alloc>
3883 _GLIBCXX_NODISCARD[[__nodiscard__]]
3884 inline bool
3885 operator>(const _CharT* __lhs,
3886 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3887 { return __rhs.compare(__lhs) < 0; }
3888
3889 // operator <=
3890 /**
3891 * @brief Test if string doesn't follow string.
3892 * @param __lhs First string.
3893 * @param __rhs Second string.
3894 * @return True if @a __lhs doesn't follow @a __rhs. False otherwise.
3895 */
3896 template<typename _CharT, typename _Traits, typename _Alloc>
3897 _GLIBCXX_NODISCARD[[__nodiscard__]]
3898 inline bool
3899 operator<=(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3900 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3901 _GLIBCXX_NOEXCEPTnoexcept
3902 { return __lhs.compare(__rhs) <= 0; }
3903
3904 /**
3905 * @brief Test if string doesn't follow C string.
3906 * @param __lhs String.
3907 * @param __rhs C string.
3908 * @return True if @a __lhs doesn't follow @a __rhs. False otherwise.
3909 */
3910 template<typename _CharT, typename _Traits, typename _Alloc>
3911 _GLIBCXX_NODISCARD[[__nodiscard__]]
3912 inline bool
3913 operator<=(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3914 const _CharT* __rhs)
3915 { return __lhs.compare(__rhs) <= 0; }
3916
3917 /**
3918 * @brief Test if C string doesn't follow string.
3919 * @param __lhs C string.
3920 * @param __rhs String.
3921 * @return True if @a __lhs doesn't follow @a __rhs. False otherwise.
3922 */
3923 template<typename _CharT, typename _Traits, typename _Alloc>
3924 _GLIBCXX_NODISCARD[[__nodiscard__]]
3925 inline bool
3926 operator<=(const _CharT* __lhs,
3927 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3928 { return __rhs.compare(__lhs) >= 0; }
3929
3930 // operator >=
3931 /**
3932 * @brief Test if string doesn't precede string.
3933 * @param __lhs First string.
3934 * @param __rhs Second string.
3935 * @return True if @a __lhs doesn't precede @a __rhs. False otherwise.
3936 */
3937 template<typename _CharT, typename _Traits, typename _Alloc>
3938 _GLIBCXX_NODISCARD[[__nodiscard__]]
3939 inline bool
3940 operator>=(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3941 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3942 _GLIBCXX_NOEXCEPTnoexcept
3943 { return __lhs.compare(__rhs) >= 0; }
3944
3945 /**
3946 * @brief Test if string doesn't precede C string.
3947 * @param __lhs String.
3948 * @param __rhs C string.
3949 * @return True if @a __lhs doesn't precede @a __rhs. False otherwise.
3950 */
3951 template<typename _CharT, typename _Traits, typename _Alloc>
3952 _GLIBCXX_NODISCARD[[__nodiscard__]]
3953 inline bool
3954 operator>=(const basic_string<_CharT, _Traits, _Alloc>& __lhs,
3955 const _CharT* __rhs)
3956 { return __lhs.compare(__rhs) >= 0; }
3957
3958 /**
3959 * @brief Test if C string doesn't precede string.
3960 * @param __lhs C string.
3961 * @param __rhs String.
3962 * @return True if @a __lhs doesn't precede @a __rhs. False otherwise.
3963 */
3964 template<typename _CharT, typename _Traits, typename _Alloc>
3965 _GLIBCXX_NODISCARD[[__nodiscard__]]
3966 inline bool
3967 operator>=(const _CharT* __lhs,
3968 const basic_string<_CharT, _Traits, _Alloc>& __rhs)
3969 { return __rhs.compare(__lhs) <= 0; }
3970#endif // three-way comparison
3971
3972 /**
3973 * @brief Swap contents of two strings.
3974 * @param __lhs First string.
3975 * @param __rhs Second string.
3976 *
3977 * Exchanges the contents of @a __lhs and @a __rhs in constant time.
3978 */
3979 template<typename _CharT, typename _Traits, typename _Alloc>
3980 _GLIBCXX20_CONSTEXPRconstexpr
3981 inline void
3982 swap(basic_string<_CharT, _Traits, _Alloc>& __lhs,
3983 basic_string<_CharT, _Traits, _Alloc>& __rhs)
3984 _GLIBCXX_NOEXCEPT_IF(noexcept(__lhs.swap(__rhs)))noexcept(noexcept(__lhs.swap(__rhs)))
3985 { __lhs.swap(__rhs); }
3986
3987
3988 /**
3989 * @brief Read stream into a string.
3990 * @param __is Input stream.
3991 * @param __str Buffer to store into.
3992 * @return Reference to the input stream.
3993 *
3994 * Stores characters from @a __is into @a __str until whitespace is
3995 * found, the end of the stream is encountered, or str.max_size()
3996 * is reached. If is.width() is non-zero, that is the limit on the
3997 * number of characters stored into @a __str. Any previous
3998 * contents of @a __str are erased.
3999 */
4000 template<typename _CharT, typename _Traits, typename _Alloc>
4001 basic_istream<_CharT, _Traits>&
4002 operator>>(basic_istream<_CharT, _Traits>& __is,
4003 basic_string<_CharT, _Traits, _Alloc>& __str);
4004
4005 template<>
4006 basic_istream<char>&
4007 operator>>(basic_istream<char>& __is, basic_string<char>& __str);
4008
4009 /**
4010 * @brief Write string to a stream.
4011 * @param __os Output stream.
4012 * @param __str String to write out.
4013 * @return Reference to the output stream.
4014 *
4015 * Output characters of @a __str into os following the same rules as for
4016 * writing a C string.
4017 */
4018 template<typename _CharT, typename _Traits, typename _Alloc>
4019 inline basic_ostream<_CharT, _Traits>&
4020 operator<<(basic_ostream<_CharT, _Traits>& __os,
4021 const basic_string<_CharT, _Traits, _Alloc>& __str)
4022 {
4023 // _GLIBCXX_RESOLVE_LIB_DEFECTS
4024 // 586. string inserter not a formatted function
4025 return __ostream_insert(__os, __str.data(), __str.size());
4026 }
4027
4028 /**
4029 * @brief Read a line from stream into a string.
4030 * @param __is Input stream.
4031 * @param __str Buffer to store into.
4032 * @param __delim Character marking end of line.
4033 * @return Reference to the input stream.
4034 *
4035 * Stores characters from @a __is into @a __str until @a __delim is
4036 * found, the end of the stream is encountered, or str.max_size()
4037 * is reached. Any previous contents of @a __str are erased. If
4038 * @a __delim is encountered, it is extracted but not stored into
4039 * @a __str.
4040 */
4041 template<typename _CharT, typename _Traits, typename _Alloc>
4042 basic_istream<_CharT, _Traits>&
4043 getline(basic_istream<_CharT, _Traits>& __is,
4044 basic_string<_CharT, _Traits, _Alloc>& __str, _CharT __delim);
4045
4046 /**
4047 * @brief Read a line from stream into a string.
4048 * @param __is Input stream.
4049 * @param __str Buffer to store into.
4050 * @return Reference to the input stream.
4051 *
4052 * Stores characters from is into @a __str until &apos;\n&apos; is
4053 * found, the end of the stream is encountered, or str.max_size()
4054 * is reached. Any previous contents of @a __str are erased. If
4055 * end of line is encountered, it is extracted but not stored into
4056 * @a __str.
4057 */
4058 template<typename _CharT, typename _Traits, typename _Alloc>
4059 inline basic_istream<_CharT, _Traits>&
4060 getline(basic_istream<_CharT, _Traits>& __is,
4061 basic_string<_CharT, _Traits, _Alloc>& __str)
4062 { return std::getline(__is, __str, __is.widen('\n')); }
4063
4064#if __cplusplus202002L >= 201103L
4065 /// Read a line from an rvalue stream into a string.
4066 template<typename _CharT, typename _Traits, typename _Alloc>
4067 inline basic_istream<_CharT, _Traits>&
4068 getline(basic_istream<_CharT, _Traits>&& __is,
4069 basic_string<_CharT, _Traits, _Alloc>& __str, _CharT __delim)
4070 { return std::getline(__is, __str, __delim); }
4071
4072 /// Read a line from an rvalue stream into a string.
4073 template<typename _CharT, typename _Traits, typename _Alloc>
4074 inline basic_istream<_CharT, _Traits>&
4075 getline(basic_istream<_CharT, _Traits>&& __is,
4076 basic_string<_CharT, _Traits, _Alloc>& __str)
4077 { return std::getline(__is, __str); }
4078#endif
4079
4080 template<>
4081 basic_istream<char>&
4082 getline(basic_istream<char>& __in, basic_string<char>& __str,
4083 char __delim);
4084
4085#ifdef _GLIBCXX_USE_WCHAR_T1
4086 template<>
4087 basic_istream<wchar_t>&
4088 getline(basic_istream<wchar_t>& __in, basic_string<wchar_t>& __str,
4089 wchar_t __delim);
4090#endif
4091
4092_GLIBCXX_END_NAMESPACE_VERSION
4093} // namespace
4094
4095#if __cplusplus202002L >= 201103L
4096
4097#include <ext/string_conversions.h>
4098#include <bits/charconv.h>
4099
4100namespace std _GLIBCXX_VISIBILITY(default)__attribute__ ((__visibility__ ("default")))
4101{
4102_GLIBCXX_BEGIN_NAMESPACE_VERSION
4103_GLIBCXX_BEGIN_NAMESPACE_CXX11namespace __cxx11 {
4104
4105#if _GLIBCXX_USE_C99_STDLIB1
4106 // 21.4 Numeric Conversions [string.conversions].
4107 inline int
4108 stoi(const string& __str, size_t* __idx = 0, int __base = 10)
4109 { return __gnu_cxx::__stoa<long, int>(&std::strtol, "stoi", __str.c_str(),
4110 __idx, __base); }
4111
4112 inline long
4113 stol(const string& __str, size_t* __idx = 0, int __base = 10)
4114 { return __gnu_cxx::__stoa(&std::strtol, "stol", __str.c_str(),
4115 __idx, __base); }
4116
4117 inline unsigned long
4118 stoul(const string& __str, size_t* __idx = 0, int __base = 10)
4119 { return __gnu_cxx::__stoa(&std::strtoul, "stoul", __str.c_str(),
4120 __idx, __base); }
4121
4122 inline long long
4123 stoll(const string& __str, size_t* __idx = 0, int __base = 10)
4124 { return __gnu_cxx::__stoa(&std::strtoll, "stoll", __str.c_str(),
4125 __idx, __base); }
4126
4127 inline unsigned long long
4128 stoull(const string& __str, size_t* __idx = 0, int __base = 10)
4129 { return __gnu_cxx::__stoa(&std::strtoull, "stoull", __str.c_str(),
4130 __idx, __base); }
4131
4132 // NB: strtof vs strtod.
4133 inline float
4134 stof(const string& __str, size_t* __idx = 0)
4135 { return __gnu_cxx::__stoa(&std::strtof, "stof", __str.c_str(), __idx); }
4136
4137 inline double
4138 stod(const string& __str, size_t* __idx = 0)
4139 { return __gnu_cxx::__stoa(&std::strtod, "stod", __str.c_str(), __idx); }
4140
4141 inline long double
4142 stold(const string& __str, size_t* __idx = 0)
4143 { return __gnu_cxx::__stoa(&std::strtold, "stold", __str.c_str(), __idx); }
4144#endif // _GLIBCXX_USE_C99_STDLIB
4145
4146 // DR 1261. Insufficent overloads for to_string / to_wstring
4147
4148 _GLIBCXX_NODISCARD[[__nodiscard__]]
4149 inline string
4150 to_string(int __val)
4151#if _GLIBCXX_USE_CXX11_ABI1 && (__CHAR_BIT__8 * __SIZEOF_INT__4) <= 32
4152 noexcept // any 32-bit value fits in the SSO buffer
4153#endif
4154 {
4155 const bool __neg = __val < 0;
4156 const unsigned __uval = __neg ? (unsigned)~__val + 1u : __val;
4157 const auto __len = __detail::__to_chars_len(__uval);
4158 string __str(__neg + __len, '-');
4159 __detail::__to_chars_10_impl(&__str[__neg], __len, __uval);
4160 return __str;
4161 }
4162
4163 _GLIBCXX_NODISCARD[[__nodiscard__]]
4164 inline string
4165 to_string(unsigned __val)
4166#if _GLIBCXX_USE_CXX11_ABI1 && (__CHAR_BIT__8 * __SIZEOF_INT__4) <= 32
4167 noexcept // any 32-bit value fits in the SSO buffer
4168#endif
4169 {
4170 string __str(__detail::__to_chars_len(__val), '\0');
4171 __detail::__to_chars_10_impl(&__str[0], __str.size(), __val);
4172 return __str;
4173 }
4174
4175 _GLIBCXX_NODISCARD[[__nodiscard__]]
4176 inline string
4177 to_string(long __val)
4178#if _GLIBCXX_USE_CXX11_ABI1 && (__CHAR_BIT__8 * __SIZEOF_LONG__8) <= 32
4179 noexcept // any 32-bit value fits in the SSO buffer
4180#endif
4181 {
4182 const bool __neg = __val < 0;
4183 const unsigned long __uval = __neg ? (unsigned long)~__val + 1ul : __val;
4184 const auto __len = __detail::__to_chars_len(__uval);
4185 string __str(__neg + __len, '-');
4186 __detail::__to_chars_10_impl(&__str[__neg], __len, __uval);
4187 return __str;
4188 }
4189
4190 _GLIBCXX_NODISCARD[[__nodiscard__]]
4191 inline string
4192 to_string(unsigned long __val)
4193#if _GLIBCXX_USE_CXX11_ABI1 && (__CHAR_BIT__8 * __SIZEOF_LONG__8) <= 32
4194 noexcept // any 32-bit value fits in the SSO buffer
4195#endif
4196 {
4197 string __str(__detail::__to_chars_len(__val), '\0');
4198 __detail::__to_chars_10_impl(&__str[0], __str.size(), __val);
4199 return __str;
4200 }
4201
4202 _GLIBCXX_NODISCARD[[__nodiscard__]]
4203 inline string
4204 to_string(long long __val)
4205 {
4206 const bool __neg = __val < 0;
4207 const unsigned long long __uval
4208 = __neg ? (unsigned long long)~__val + 1ull : __val;
4209 const auto __len = __detail::__to_chars_len(__uval);
4210 string __str(__neg + __len, '-');
4211 __detail::__to_chars_10_impl(&__str[__neg], __len, __uval);
4212 return __str;
4213 }
4214
4215 _GLIBCXX_NODISCARD[[__nodiscard__]]
4216 inline string
4217 to_string(unsigned long long __val)
4218 {
4219 string __str(__detail::__to_chars_len(__val), '\0');
4220 __detail::__to_chars_10_impl(&__str[0], __str.size(), __val);
4221 return __str;
4222 }
4223
4224#if _GLIBCXX_USE_C99_STDIO1
4225 // NB: (v)snprintf vs sprintf.
4226
4227 _GLIBCXX_NODISCARD[[__nodiscard__]]
4228 inline string
4229 to_string(float __val)
4230 {
4231 const int __n =
4232 __gnu_cxx::__numeric_traits<float>::__max_exponent10 + 20;
4233 return __gnu_cxx::__to_xstring<string>(&std::vsnprintf, __n,
4234 "%f", __val);
4235 }
4236
4237 _GLIBCXX_NODISCARD[[__nodiscard__]]
4238 inline string
4239 to_string(double __val)
4240 {
4241 const int __n =
4242 __gnu_cxx::__numeric_traits<double>::__max_exponent10 + 20;
4243 return __gnu_cxx::__to_xstring<string>(&std::vsnprintf, __n,
4244 "%f", __val);
4245 }
4246
4247 _GLIBCXX_NODISCARD[[__nodiscard__]]
4248 inline string
4249 to_string(long double __val)
4250 {
4251 const int __n =
4252 __gnu_cxx::__numeric_traits<long double>::__max_exponent10 + 20;
4253 return __gnu_cxx::__to_xstring<string>(&std::vsnprintf, __n,
4254 "%Lf", __val);
4255 }
4256#endif // _GLIBCXX_USE_C99_STDIO
4257
4258#if defined(_GLIBCXX_USE_WCHAR_T1) && _GLIBCXX_USE_C99_WCHAR1
4259 inline int
4260 stoi(const wstring& __str, size_t* __idx = 0, int __base = 10)
4261 { return __gnu_cxx::__stoa<long, int>(&std::wcstol, "stoi", __str.c_str(),
4262 __idx, __base); }
4263
4264 inline long
4265 stol(const wstring& __str, size_t* __idx = 0, int __base = 10)
4266 { return __gnu_cxx::__stoa(&std::wcstol, "stol", __str.c_str(),
4267 __idx, __base); }
4268
4269 inline unsigned long
4270 stoul(const wstring& __str, size_t* __idx = 0, int __base = 10)
4271 { return __gnu_cxx::__stoa(&std::wcstoul, "stoul", __str.c_str(),
4272 __idx, __base); }
4273
4274 inline long long
4275 stoll(const wstring& __str, size_t* __idx = 0, int __base = 10)
4276 { return __gnu_cxx::__stoa(&std::wcstoll, "stoll", __str.c_str(),
4277 __idx, __base); }
4278
4279 inline unsigned long long
4280 stoull(const wstring& __str, size_t* __idx = 0, int __base = 10)
4281 { return __gnu_cxx::__stoa(&std::wcstoull, "stoull", __str.c_str(),
4282 __idx, __base); }
4283
4284 // NB: wcstof vs wcstod.
4285 inline float
4286 stof(const wstring& __str, size_t* __idx = 0)
4287 { return __gnu_cxx::__stoa(&std::wcstof, "stof", __str.c_str(), __idx); }
4288
4289 inline double
4290 stod(const wstring& __str, size_t* __idx = 0)
4291 { return __gnu_cxx::__stoa(&std::wcstod, "stod", __str.c_str(), __idx); }
4292
4293 inline long double
4294 stold(const wstring& __str, size_t* __idx = 0)
4295 { return __gnu_cxx::__stoa(&std::wcstold, "stold", __str.c_str(), __idx); }
4296
4297#ifndef _GLIBCXX_HAVE_BROKEN_VSWPRINTF
4298 // DR 1261.
4299 _GLIBCXX_NODISCARD[[__nodiscard__]]
4300 inline wstring
4301 to_wstring(int __val)
4302 { return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf, 4 * sizeof(int),
4303 L"%d", __val); }
4304
4305 _GLIBCXX_NODISCARD[[__nodiscard__]]
4306 inline wstring
4307 to_wstring(unsigned __val)
4308 { return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf,
4309 4 * sizeof(unsigned),
4310 L"%u", __val); }
4311
4312 _GLIBCXX_NODISCARD[[__nodiscard__]]
4313 inline wstring
4314 to_wstring(long __val)
4315 { return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf, 4 * sizeof(long),
4316 L"%ld", __val); }
4317
4318 _GLIBCXX_NODISCARD[[__nodiscard__]]
4319 inline wstring
4320 to_wstring(unsigned long __val)
4321 { return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf,
4322 4 * sizeof(unsigned long),
4323 L"%lu", __val); }
4324
4325 _GLIBCXX_NODISCARD[[__nodiscard__]]
4326 inline wstring
4327 to_wstring(long long __val)
4328 { return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf,
4329 4 * sizeof(long long),
4330 L"%lld", __val); }
4331
4332 _GLIBCXX_NODISCARD[[__nodiscard__]]
4333 inline wstring
4334 to_wstring(unsigned long long __val)
4335 { return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf,
4336 4 * sizeof(unsigned long long),
4337 L"%llu", __val); }
4338
4339 _GLIBCXX_NODISCARD[[__nodiscard__]]
4340 inline wstring
4341 to_wstring(float __val)
4342 {
4343 const int __n =
4344 __gnu_cxx::__numeric_traits<float>::__max_exponent10 + 20;
4345 return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf, __n,
4346 L"%f", __val);
4347 }
4348
4349 _GLIBCXX_NODISCARD[[__nodiscard__]]
4350 inline wstring
4351 to_wstring(double __val)
4352 {
4353 const int __n =
4354 __gnu_cxx::__numeric_traits<double>::__max_exponent10 + 20;
4355 return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf, __n,
4356 L"%f", __val);
4357 }
4358
4359 _GLIBCXX_NODISCARD[[__nodiscard__]]
4360 inline wstring
4361 to_wstring(long double __val)
4362 {
4363 const int __n =
4364 __gnu_cxx::__numeric_traits<long double>::__max_exponent10 + 20;
4365 return __gnu_cxx::__to_xstring<wstring>(&std::vswprintf, __n,
4366 L"%Lf", __val);
4367 }
4368#endif // _GLIBCXX_HAVE_BROKEN_VSWPRINTF
4369#endif // _GLIBCXX_USE_WCHAR_T && _GLIBCXX_USE_C99_WCHAR
4370
4371_GLIBCXX_END_NAMESPACE_CXX11}
4372_GLIBCXX_END_NAMESPACE_VERSION
4373} // namespace
4374
4375#endif /* C++11 */
4376
4377#if __cplusplus202002L >= 201103L
4378
4379#include <bits/functional_hash.h>
4380
4381namespace std _GLIBCXX_VISIBILITY(default)__attribute__ ((__visibility__ ("default")))
4382{
4383_GLIBCXX_BEGIN_NAMESPACE_VERSION
4384
4385 // _GLIBCXX_RESOLVE_LIB_DEFECTS
4386 // 3705. Hashability shouldn't depend on basic_string's allocator
4387
4388 template<typename _CharT, typename _Alloc,
4389 typename _StrT = basic_string<_CharT, char_traits<_CharT>, _Alloc>>
4390 struct __str_hash_base
4391 : public __hash_base<size_t, _StrT>
4392 {
4393 [[__nodiscard__]]
4394 size_t
4395 operator()(const _StrT& __s) const noexcept
4396 { return _Hash_impl::hash(__s.data(), __s.length() * sizeof(_CharT)); }
4397 };
4398
4399#ifndef _GLIBCXX_COMPATIBILITY_CXX0X
4400 /// std::hash specialization for string.
4401 template<typename _Alloc>
4402 struct hash<basic_string<char, char_traits<char>, _Alloc>>
4403 : public __str_hash_base<char, _Alloc>
4404 { };
4405
4406 /// std::hash specialization for wstring.
4407 template<typename _Alloc>
4408 struct hash<basic_string<wchar_t, char_traits<wchar_t>, _Alloc>>
4409 : public __str_hash_base<wchar_t, _Alloc>
4410 { };
4411
4412 template<typename _Alloc>
4413 struct __is_fast_hash<hash<basic_string<wchar_t, char_traits<wchar_t>,
4414 _Alloc>>>
4415 : std::false_type
4416 { };
4417#endif /* _GLIBCXX_COMPATIBILITY_CXX0X */
4418
4419#ifdef _GLIBCXX_USE_CHAR8_T1
4420 /// std::hash specialization for u8string.
4421 template<typename _Alloc>
4422 struct hash<basic_string<char8_t, char_traits<char8_t>, _Alloc>>
4423 : public __str_hash_base<char8_t, _Alloc>
4424 { };
4425#endif
4426
4427 /// std::hash specialization for u16string.
4428 template<typename _Alloc>
4429 struct hash<basic_string<char16_t, char_traits<char16_t>, _Alloc>>
4430 : public __str_hash_base<char16_t, _Alloc>
4431 { };
4432
4433 /// std::hash specialization for u32string.
4434 template<typename _Alloc>
4435 struct hash<basic_string<char32_t, char_traits<char32_t>, _Alloc>>
4436 : public __str_hash_base<char32_t, _Alloc>
4437 { };
4438
4439#if ! _GLIBCXX_INLINE_VERSION0
4440 // PR libstdc++/105907 - __is_fast_hash affects unordered container ABI.
4441 template<> struct __is_fast_hash<hash<string>> : std::false_type { };
4442 template<> struct __is_fast_hash<hash<wstring>> : std::false_type { };
4443 template<> struct __is_fast_hash<hash<u16string>> : std::false_type { };
4444 template<> struct __is_fast_hash<hash<u32string>> : std::false_type { };
4445#ifdef _GLIBCXX_USE_CHAR8_T1
4446 template<> struct __is_fast_hash<hash<u8string>> : std::false_type { };
4447#endif
4448#else
4449 // For versioned namespace, assume every std::hash<basic_string<>> is slow.
4450 template<typename _CharT, typename _Traits, typename _Alloc>
4451 struct __is_fast_hash<hash<basic_string<_CharT, _Traits, _Alloc>>>
4452 : std::false_type
4453 { };
4454#endif
4455
4456#if __cplusplus202002L >= 201402L
4457
4458#define __cpp_lib_string_udls201304L 201304L
4459
4460 inline namespace literals
4461 {
4462 inline namespace string_literals
4463 {
4464#pragma GCC diagnostic push
4465#pragma GCC diagnostic ignored "-Wliteral-suffix"
4466
4467#if __cpp_lib_constexpr_string201907L >= 201907L
4468# define _GLIBCXX_STRING_CONSTEXPR constexpr
4469#else
4470# define _GLIBCXX_STRING_CONSTEXPR
4471#endif
4472
4473 _GLIBCXX_DEFAULT_ABI_TAG__attribute ((__abi_tag__ ("cxx11"))) _GLIBCXX_STRING_CONSTEXPR
4474 inline basic_string<char>
4475 operator""s(const char* __str, size_t __len)
4476 { return basic_string<char>{__str, __len}; }
4477
4478 _GLIBCXX_DEFAULT_ABI_TAG__attribute ((__abi_tag__ ("cxx11"))) _GLIBCXX_STRING_CONSTEXPR
4479 inline basic_string<wchar_t>
4480 operator""s(const wchar_t* __str, size_t __len)
4481 { return basic_string<wchar_t>{__str, __len}; }
4482
4483#ifdef _GLIBCXX_USE_CHAR8_T1
4484 _GLIBCXX_DEFAULT_ABI_TAG__attribute ((__abi_tag__ ("cxx11"))) _GLIBCXX_STRING_CONSTEXPR
4485 inline basic_string<char8_t>
4486 operator""s(const char8_t* __str, size_t __len)
4487 { return basic_string<char8_t>{__str, __len}; }
4488#endif
4489
4490 _GLIBCXX_DEFAULT_ABI_TAG__attribute ((__abi_tag__ ("cxx11"))) _GLIBCXX_STRING_CONSTEXPR
4491 inline basic_string<char16_t>
4492 operator""s(const char16_t* __str, size_t __len)
4493 { return basic_string<char16_t>{__str, __len}; }
4494
4495 _GLIBCXX_DEFAULT_ABI_TAG__attribute ((__abi_tag__ ("cxx11"))) _GLIBCXX_STRING_CONSTEXPR
4496 inline basic_string<char32_t>
4497 operator""s(const char32_t* __str, size_t __len)
4498 { return basic_string<char32_t>{__str, __len}; }
4499
4500#undef _GLIBCXX_STRING_CONSTEXPR
4501#pragma GCC diagnostic pop
4502 } // inline namespace string_literals
4503 } // inline namespace literals
4504
4505#if __cplusplus202002L >= 201703L
4506 namespace __detail::__variant
4507 {
4508 template<typename> struct _Never_valueless_alt; // see <variant>
4509
4510 // Provide the strong exception-safety guarantee when emplacing a
4511 // basic_string into a variant, but only if moving the string cannot throw.
4512 template<typename _Tp, typename _Traits, typename _Alloc>
4513 struct _Never_valueless_alt<std::basic_string<_Tp, _Traits, _Alloc>>
4514 : __and_<
4515 is_nothrow_move_constructible<std::basic_string<_Tp, _Traits, _Alloc>>,
4516 is_nothrow_move_assignable<std::basic_string<_Tp, _Traits, _Alloc>>
4517 >::type
4518 { };
4519 } // namespace __detail::__variant
4520#endif // C++17
4521#endif // C++14
4522
4523_GLIBCXX_END_NAMESPACE_VERSION
4524} // namespace std
4525
4526#endif // C++11
4527
4528#endif /* _BASIC_STRING_H */