2 //===--------------------------- string -----------------------------------===//
4 // The LLVM Compiler Infrastructure
6 // This file is distributed under the University of Illinois Open Source
7 // License. See LICENSE.TXT for details.
9 //===----------------------------------------------------------------------===//
11 #ifndef _LIBCPP_STRING
12 #define _LIBCPP_STRING
20 template <class stateT>
26 fpos(streamoff = streamoff());
28 operator streamoff() const;
33 fpos& operator+=(streamoff);
34 fpos operator+ (streamoff) const;
35 fpos& operator-=(streamoff);
36 fpos operator- (streamoff) const;
39 template <class stateT> streamoff operator-(const fpos<stateT>& x, const fpos<stateT>& y);
41 template <class stateT> bool operator==(const fpos<stateT>& x, const fpos<stateT>& y);
42 template <class stateT> bool operator!=(const fpos<stateT>& x, const fpos<stateT>& y);
44 template <class charT>
47 typedef charT char_type;
49 typedef streamoff off_type;
50 typedef streampos pos_type;
51 typedef mbstate_t state_type;
53 static void assign(char_type& c1, const char_type& c2) noexcept;
54 static constexpr bool eq(char_type c1, char_type c2) noexcept;
55 static constexpr bool lt(char_type c1, char_type c2) noexcept;
57 static int compare(const char_type* s1, const char_type* s2, size_t n);
58 static size_t length(const char_type* s);
59 static const char_type* find(const char_type* s, size_t n, const char_type& a);
60 static char_type* move(char_type* s1, const char_type* s2, size_t n);
61 static char_type* copy(char_type* s1, const char_type* s2, size_t n);
62 static char_type* assign(char_type* s, size_t n, char_type a);
64 static constexpr int_type not_eof(int_type c) noexcept;
65 static constexpr char_type to_char_type(int_type c) noexcept;
66 static constexpr int_type to_int_type(char_type c) noexcept;
67 static constexpr bool eq_int_type(int_type c1, int_type c2) noexcept;
68 static constexpr int_type eof() noexcept;
71 template <> struct char_traits<char>;
72 template <> struct char_traits<wchar_t>;
74 template<class charT, class traits = char_traits<charT>, class Allocator = allocator<charT> >
79 typedef traits traits_type;
80 typedef typename traits_type::char_type value_type;
81 typedef Allocator allocator_type;
82 typedef typename allocator_type::size_type size_type;
83 typedef typename allocator_type::difference_type difference_type;
84 typedef typename allocator_type::reference reference;
85 typedef typename allocator_type::const_reference const_reference;
86 typedef typename allocator_type::pointer pointer;
87 typedef typename allocator_type::const_pointer const_pointer;
88 typedef implementation-defined iterator;
89 typedef implementation-defined const_iterator;
90 typedef std::reverse_iterator<iterator> reverse_iterator;
91 typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
93 static const size_type npos = -1;
96 noexcept(is_nothrow_default_constructible<allocator_type>::value);
97 explicit basic_string(const allocator_type& a);
98 basic_string(const basic_string& str);
99 basic_string(basic_string&& str)
100 noexcept(is_nothrow_move_constructible<allocator_type>::value);
101 basic_string(const basic_string& str, size_type pos,
102 const allocator_type& a = allocator_type());
103 basic_string(const basic_string& str, size_type pos, size_type n,
104 const Allocator& a = Allocator());
105 basic_string(const value_type* s, const allocator_type& a = allocator_type());
106 basic_string(const value_type* s, size_type n, const allocator_type& a = allocator_type());
107 basic_string(size_type n, value_type c, const allocator_type& a = allocator_type());
108 template<class InputIterator>
109 basic_string(InputIterator begin, InputIterator end,
110 const allocator_type& a = allocator_type());
111 basic_string(initializer_list<value_type>, const Allocator& = Allocator());
112 basic_string(const basic_string&, const Allocator&);
113 basic_string(basic_string&&, const Allocator&);
117 basic_string& operator=(const basic_string& str);
118 basic_string& operator=(basic_string&& str)
120 allocator_type::propagate_on_container_move_assignment::value ||
121 allocator_type::is_always_equal::value ); // C++17
122 basic_string& operator=(const value_type* s);
123 basic_string& operator=(value_type c);
124 basic_string& operator=(initializer_list<value_type>);
126 iterator begin() noexcept;
127 const_iterator begin() const noexcept;
128 iterator end() noexcept;
129 const_iterator end() const noexcept;
131 reverse_iterator rbegin() noexcept;
132 const_reverse_iterator rbegin() const noexcept;
133 reverse_iterator rend() noexcept;
134 const_reverse_iterator rend() const noexcept;
136 const_iterator cbegin() const noexcept;
137 const_iterator cend() const noexcept;
138 const_reverse_iterator crbegin() const noexcept;
139 const_reverse_iterator crend() const noexcept;
141 size_type size() const noexcept;
142 size_type length() const noexcept;
143 size_type max_size() const noexcept;
144 size_type capacity() const noexcept;
146 void resize(size_type n, value_type c);
147 void resize(size_type n);
149 void reserve(size_type res_arg = 0);
150 void shrink_to_fit();
151 void clear() noexcept;
152 bool empty() const noexcept;
154 const_reference operator[](size_type pos) const;
155 reference operator[](size_type pos);
157 const_reference at(size_type n) const;
158 reference at(size_type n);
160 basic_string& operator+=(const basic_string& str);
161 basic_string& operator+=(const value_type* s);
162 basic_string& operator+=(value_type c);
163 basic_string& operator+=(initializer_list<value_type>);
165 basic_string& append(const basic_string& str);
166 basic_string& append(const basic_string& str, size_type pos, size_type n=npos); //C++14
167 basic_string& append(const value_type* s, size_type n);
168 basic_string& append(const value_type* s);
169 basic_string& append(size_type n, value_type c);
170 template<class InputIterator>
171 basic_string& append(InputIterator first, InputIterator last);
172 basic_string& append(initializer_list<value_type>);
174 void push_back(value_type c);
177 const_reference front() const;
179 const_reference back() const;
181 basic_string& assign(const basic_string& str);
182 basic_string& assign(basic_string&& str);
183 basic_string& assign(const basic_string& str, size_type pos, size_type n=npos); // C++14
184 basic_string& assign(const value_type* s, size_type n);
185 basic_string& assign(const value_type* s);
186 basic_string& assign(size_type n, value_type c);
187 template<class InputIterator>
188 basic_string& assign(InputIterator first, InputIterator last);
189 basic_string& assign(initializer_list<value_type>);
191 basic_string& insert(size_type pos1, const basic_string& str);
192 basic_string& insert(size_type pos1, const basic_string& str,
193 size_type pos2, size_type n);
194 basic_string& insert(size_type pos, const value_type* s, size_type n=npos); //C++14
195 basic_string& insert(size_type pos, const value_type* s);
196 basic_string& insert(size_type pos, size_type n, value_type c);
197 iterator insert(const_iterator p, value_type c);
198 iterator insert(const_iterator p, size_type n, value_type c);
199 template<class InputIterator>
200 iterator insert(const_iterator p, InputIterator first, InputIterator last);
201 iterator insert(const_iterator p, initializer_list<value_type>);
203 basic_string& erase(size_type pos = 0, size_type n = npos);
204 iterator erase(const_iterator position);
205 iterator erase(const_iterator first, const_iterator last);
207 basic_string& replace(size_type pos1, size_type n1, const basic_string& str);
208 basic_string& replace(size_type pos1, size_type n1, const basic_string& str,
209 size_type pos2, size_type n2=npos); // C++14
210 basic_string& replace(size_type pos, size_type n1, const value_type* s, size_type n2);
211 basic_string& replace(size_type pos, size_type n1, const value_type* s);
212 basic_string& replace(size_type pos, size_type n1, size_type n2, value_type c);
213 basic_string& replace(const_iterator i1, const_iterator i2, const basic_string& str);
214 basic_string& replace(const_iterator i1, const_iterator i2, const value_type* s, size_type n);
215 basic_string& replace(const_iterator i1, const_iterator i2, const value_type* s);
216 basic_string& replace(const_iterator i1, const_iterator i2, size_type n, value_type c);
217 template<class InputIterator>
218 basic_string& replace(const_iterator i1, const_iterator i2, InputIterator j1, InputIterator j2);
219 basic_string& replace(const_iterator i1, const_iterator i2, initializer_list<value_type>);
221 size_type copy(value_type* s, size_type n, size_type pos = 0) const;
222 basic_string substr(size_type pos = 0, size_type n = npos) const;
224 void swap(basic_string& str)
225 noexcept(allocator_traits<allocator_type>::propagate_on_container_swap::value ||
226 allocator_traits<allocator_type>::is_always_equal::value); // C++17
228 const value_type* c_str() const noexcept;
229 const value_type* data() const noexcept;
230 value_type* data() noexcept; // C++17
232 allocator_type get_allocator() const noexcept;
234 size_type find(const basic_string& str, size_type pos = 0) const noexcept;
235 size_type find(const value_type* s, size_type pos, size_type n) const noexcept;
236 size_type find(const value_type* s, size_type pos = 0) const noexcept;
237 size_type find(value_type c, size_type pos = 0) const noexcept;
239 size_type rfind(const basic_string& str, size_type pos = npos) const noexcept;
240 size_type rfind(const value_type* s, size_type pos, size_type n) const noexcept;
241 size_type rfind(const value_type* s, size_type pos = npos) const noexcept;
242 size_type rfind(value_type c, size_type pos = npos) const noexcept;
244 size_type find_first_of(const basic_string& str, size_type pos = 0) const noexcept;
245 size_type find_first_of(const value_type* s, size_type pos, size_type n) const noexcept;
246 size_type find_first_of(const value_type* s, size_type pos = 0) const noexcept;
247 size_type find_first_of(value_type c, size_type pos = 0) const noexcept;
249 size_type find_last_of(const basic_string& str, size_type pos = npos) const noexcept;
250 size_type find_last_of(const value_type* s, size_type pos, size_type n) const noexcept;
251 size_type find_last_of(const value_type* s, size_type pos = npos) const noexcept;
252 size_type find_last_of(value_type c, size_type pos = npos) const noexcept;
254 size_type find_first_not_of(const basic_string& str, size_type pos = 0) const noexcept;
255 size_type find_first_not_of(const value_type* s, size_type pos, size_type n) const noexcept;
256 size_type find_first_not_of(const value_type* s, size_type pos = 0) const noexcept;
257 size_type find_first_not_of(value_type c, size_type pos = 0) const noexcept;
259 size_type find_last_not_of(const basic_string& str, size_type pos = npos) const noexcept;
260 size_type find_last_not_of(const value_type* s, size_type pos, size_type n) const noexcept;
261 size_type find_last_not_of(const value_type* s, size_type pos = npos) const noexcept;
262 size_type find_last_not_of(value_type c, size_type pos = npos) const noexcept;
264 int compare(const basic_string& str) const noexcept;
265 int compare(size_type pos1, size_type n1, const basic_string& str) const;
266 int compare(size_type pos1, size_type n1, const basic_string& str,
267 size_type pos2, size_type n2=npos) const; // C++14
268 int compare(const value_type* s) const noexcept;
269 int compare(size_type pos1, size_type n1, const value_type* s) const;
270 int compare(size_type pos1, size_type n1, const value_type* s, size_type n2) const;
272 bool __invariants() const;
275 template<class charT, class traits, class Allocator>
276 basic_string<charT, traits, Allocator>
277 operator+(const basic_string<charT, traits, Allocator>& lhs,
278 const basic_string<charT, traits, Allocator>& rhs);
280 template<class charT, class traits, class Allocator>
281 basic_string<charT, traits, Allocator>
282 operator+(const charT* lhs , const basic_string<charT,traits,Allocator>&rhs);
284 template<class charT, class traits, class Allocator>
285 basic_string<charT, traits, Allocator>
286 operator+(charT lhs, const basic_string<charT,traits,Allocator>& rhs);
288 template<class charT, class traits, class Allocator>
289 basic_string<charT, traits, Allocator>
290 operator+(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs);
292 template<class charT, class traits, class Allocator>
293 basic_string<charT, traits, Allocator>
294 operator+(const basic_string<charT, traits, Allocator>& lhs, charT rhs);
296 template<class charT, class traits, class Allocator>
297 bool operator==(const basic_string<charT, traits, Allocator>& lhs,
298 const basic_string<charT, traits, Allocator>& rhs) noexcept;
300 template<class charT, class traits, class Allocator>
301 bool operator==(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept;
303 template<class charT, class traits, class Allocator>
304 bool operator==(const basic_string<charT,traits,Allocator>& lhs, const charT* rhs) noexcept;
306 template<class charT, class traits, class Allocator>
307 bool operator!=(const basic_string<charT,traits,Allocator>& lhs,
308 const basic_string<charT, traits, Allocator>& rhs) noexcept;
310 template<class charT, class traits, class Allocator>
311 bool operator!=(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept;
313 template<class charT, class traits, class Allocator>
314 bool operator!=(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept;
316 template<class charT, class traits, class Allocator>
317 bool operator< (const basic_string<charT, traits, Allocator>& lhs,
318 const basic_string<charT, traits, Allocator>& rhs) noexcept;
320 template<class charT, class traits, class Allocator>
321 bool operator< (const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept;
323 template<class charT, class traits, class Allocator>
324 bool operator< (const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept;
326 template<class charT, class traits, class Allocator>
327 bool operator> (const basic_string<charT, traits, Allocator>& lhs,
328 const basic_string<charT, traits, Allocator>& rhs) noexcept;
330 template<class charT, class traits, class Allocator>
331 bool operator> (const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept;
333 template<class charT, class traits, class Allocator>
334 bool operator> (const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept;
336 template<class charT, class traits, class Allocator>
337 bool operator<=(const basic_string<charT, traits, Allocator>& lhs,
338 const basic_string<charT, traits, Allocator>& rhs) noexcept;
340 template<class charT, class traits, class Allocator>
341 bool operator<=(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept;
343 template<class charT, class traits, class Allocator>
344 bool operator<=(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept;
346 template<class charT, class traits, class Allocator>
347 bool operator>=(const basic_string<charT, traits, Allocator>& lhs,
348 const basic_string<charT, traits, Allocator>& rhs) noexcept;
350 template<class charT, class traits, class Allocator>
351 bool operator>=(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept;
353 template<class charT, class traits, class Allocator>
354 bool operator>=(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept;
356 template<class charT, class traits, class Allocator>
357 void swap(basic_string<charT, traits, Allocator>& lhs,
358 basic_string<charT, traits, Allocator>& rhs)
359 noexcept(noexcept(lhs.swap(rhs)));
361 template<class charT, class traits, class Allocator>
362 basic_istream<charT, traits>&
363 operator>>(basic_istream<charT, traits>& is, basic_string<charT, traits, Allocator>& str);
365 template<class charT, class traits, class Allocator>
366 basic_ostream<charT, traits>&
367 operator<<(basic_ostream<charT, traits>& os, const basic_string<charT, traits, Allocator>& str);
369 template<class charT, class traits, class Allocator>
370 basic_istream<charT, traits>&
371 getline(basic_istream<charT, traits>& is, basic_string<charT, traits, Allocator>& str,
374 template<class charT, class traits, class Allocator>
375 basic_istream<charT, traits>&
376 getline(basic_istream<charT, traits>& is, basic_string<charT, traits, Allocator>& str);
378 typedef basic_string<char> string;
379 typedef basic_string<wchar_t> wstring;
380 typedef basic_string<char16_t> u16string;
381 typedef basic_string<char32_t> u32string;
383 int stoi (const string& str, size_t* idx = 0, int base = 10);
384 long stol (const string& str, size_t* idx = 0, int base = 10);
385 unsigned long stoul (const string& str, size_t* idx = 0, int base = 10);
386 long long stoll (const string& str, size_t* idx = 0, int base = 10);
387 unsigned long long stoull(const string& str, size_t* idx = 0, int base = 10);
389 float stof (const string& str, size_t* idx = 0);
390 double stod (const string& str, size_t* idx = 0);
391 long double stold(const string& str, size_t* idx = 0);
393 string to_string(int val);
394 string to_string(unsigned val);
395 string to_string(long val);
396 string to_string(unsigned long val);
397 string to_string(long long val);
398 string to_string(unsigned long long val);
399 string to_string(float val);
400 string to_string(double val);
401 string to_string(long double val);
403 int stoi (const wstring& str, size_t* idx = 0, int base = 10);
404 long stol (const wstring& str, size_t* idx = 0, int base = 10);
405 unsigned long stoul (const wstring& str, size_t* idx = 0, int base = 10);
406 long long stoll (const wstring& str, size_t* idx = 0, int base = 10);
407 unsigned long long stoull(const wstring& str, size_t* idx = 0, int base = 10);
409 float stof (const wstring& str, size_t* idx = 0);
410 double stod (const wstring& str, size_t* idx = 0);
411 long double stold(const wstring& str, size_t* idx = 0);
413 wstring to_wstring(int val);
414 wstring to_wstring(unsigned val);
415 wstring to_wstring(long val);
416 wstring to_wstring(unsigned long val);
417 wstring to_wstring(long long val);
418 wstring to_wstring(unsigned long long val);
419 wstring to_wstring(float val);
420 wstring to_wstring(double val);
421 wstring to_wstring(long double val);
423 template <> struct hash<string>;
424 template <> struct hash<u16string>;
425 template <> struct hash<u32string>;
426 template <> struct hash<wstring>;
428 basic_string<char> operator "" s( const char *str, size_t len ); // C++14
429 basic_string<wchar_t> operator "" s( const wchar_t *str, size_t len ); // C++14
430 basic_string<char16_t> operator "" s( const char16_t *str, size_t len ); // C++14
431 basic_string<char32_t> operator "" s( const char32_t *str, size_t len ); // C++14
440 #include <cstdio> // For EOF.
447 #include <type_traits>
448 #include <initializer_list>
449 #include <__functional_base>
450 #ifndef _LIBCPP_HAS_NO_UNICODE_CHARS
453 #if defined(_LIBCPP_NO_EXCEPTIONS)
457 #include <__undef_min_max>
461 #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
462 #pragma GCC system_header
465 _LIBCPP_BEGIN_NAMESPACE_STD
469 template <class _StateT>
470 class _LIBCPP_TYPE_VIS_ONLY fpos
476 _LIBCPP_INLINE_VISIBILITY fpos(streamoff __off = streamoff()) : __st_(), __off_(__off) {}
478 _LIBCPP_INLINE_VISIBILITY operator streamoff() const {return __off_;}
480 _LIBCPP_INLINE_VISIBILITY _StateT state() const {return __st_;}
481 _LIBCPP_INLINE_VISIBILITY void state(_StateT __st) {__st_ = __st;}
483 _LIBCPP_INLINE_VISIBILITY fpos& operator+=(streamoff __off) {__off_ += __off; return *this;}
484 _LIBCPP_INLINE_VISIBILITY fpos operator+ (streamoff __off) const {fpos __t(*this); __t += __off; return __t;}
485 _LIBCPP_INLINE_VISIBILITY fpos& operator-=(streamoff __off) {__off_ -= __off; return *this;}
486 _LIBCPP_INLINE_VISIBILITY fpos operator- (streamoff __off) const {fpos __t(*this); __t -= __off; return __t;}
489 template <class _StateT>
490 inline _LIBCPP_INLINE_VISIBILITY
491 streamoff operator-(const fpos<_StateT>& __x, const fpos<_StateT>& __y)
492 {return streamoff(__x) - streamoff(__y);}
494 template <class _StateT>
495 inline _LIBCPP_INLINE_VISIBILITY
496 bool operator==(const fpos<_StateT>& __x, const fpos<_StateT>& __y)
497 {return streamoff(__x) == streamoff(__y);}
499 template <class _StateT>
500 inline _LIBCPP_INLINE_VISIBILITY
501 bool operator!=(const fpos<_StateT>& __x, const fpos<_StateT>& __y)
502 {return streamoff(__x) != streamoff(__y);}
506 template <class _CharT>
507 struct _LIBCPP_TYPE_VIS_ONLY char_traits
509 typedef _CharT char_type;
510 typedef int int_type;
511 typedef streamoff off_type;
512 typedef streampos pos_type;
513 typedef mbstate_t state_type;
515 static inline void assign(char_type& __c1, const char_type& __c2) _NOEXCEPT
517 static inline _LIBCPP_CONSTEXPR bool eq(char_type __c1, char_type __c2) _NOEXCEPT
518 {return __c1 == __c2;}
519 static inline _LIBCPP_CONSTEXPR bool lt(char_type __c1, char_type __c2) _NOEXCEPT
520 {return __c1 < __c2;}
522 static int compare(const char_type* __s1, const char_type* __s2, size_t __n);
523 _LIBCPP_INLINE_VISIBILITY
524 static size_t length(const char_type* __s);
525 _LIBCPP_INLINE_VISIBILITY
526 static const char_type* find(const char_type* __s, size_t __n, const char_type& __a);
527 static char_type* move(char_type* __s1, const char_type* __s2, size_t __n);
528 _LIBCPP_INLINE_VISIBILITY
529 static char_type* copy(char_type* __s1, const char_type* __s2, size_t __n);
530 _LIBCPP_INLINE_VISIBILITY
531 static char_type* assign(char_type* __s, size_t __n, char_type __a);
533 static inline _LIBCPP_CONSTEXPR int_type not_eof(int_type __c) _NOEXCEPT
534 {return eq_int_type(__c, eof()) ? ~eof() : __c;}
535 static inline _LIBCPP_CONSTEXPR char_type to_char_type(int_type __c) _NOEXCEPT
536 {return char_type(__c);}
537 static inline _LIBCPP_CONSTEXPR int_type to_int_type(char_type __c) _NOEXCEPT
538 {return int_type(__c);}
539 static inline _LIBCPP_CONSTEXPR bool eq_int_type(int_type __c1, int_type __c2) _NOEXCEPT
540 {return __c1 == __c2;}
541 static inline _LIBCPP_CONSTEXPR int_type eof() _NOEXCEPT
542 {return int_type(EOF);}
545 template <class _CharT>
547 char_traits<_CharT>::compare(const char_type* __s1, const char_type* __s2, size_t __n)
549 for (; __n; --__n, ++__s1, ++__s2)
551 if (lt(*__s1, *__s2))
553 if (lt(*__s2, *__s1))
559 template <class _CharT>
562 char_traits<_CharT>::length(const char_type* __s)
565 for (; !eq(*__s, char_type(0)); ++__s)
570 template <class _CharT>
573 char_traits<_CharT>::find(const char_type* __s, size_t __n, const char_type& __a)
584 template <class _CharT>
586 char_traits<_CharT>::move(char_type* __s1, const char_type* __s2, size_t __n)
588 char_type* __r = __s1;
591 for (; __n; --__n, ++__s1, ++__s2)
592 assign(*__s1, *__s2);
594 else if (__s2 < __s1)
599 assign(*--__s1, *--__s2);
604 template <class _CharT>
607 char_traits<_CharT>::copy(char_type* __s1, const char_type* __s2, size_t __n)
609 _LIBCPP_ASSERT(__s2 < __s1 || __s2 >= __s1+__n, "char_traits::copy overlapped range");
610 char_type* __r = __s1;
611 for (; __n; --__n, ++__s1, ++__s2)
612 assign(*__s1, *__s2);
616 template <class _CharT>
619 char_traits<_CharT>::assign(char_type* __s, size_t __n, char_type __a)
621 char_type* __r = __s;
622 for (; __n; --__n, ++__s)
630 struct _LIBCPP_TYPE_VIS_ONLY char_traits<char>
632 typedef char char_type;
633 typedef int int_type;
634 typedef streamoff off_type;
635 typedef streampos pos_type;
636 typedef mbstate_t state_type;
638 static inline void assign(char_type& __c1, const char_type& __c2) _NOEXCEPT
640 static inline _LIBCPP_CONSTEXPR bool eq(char_type __c1, char_type __c2) _NOEXCEPT
641 {return __c1 == __c2;}
642 static inline _LIBCPP_CONSTEXPR bool lt(char_type __c1, char_type __c2) _NOEXCEPT
643 {return (unsigned char)__c1 < (unsigned char)__c2;}
645 static inline int compare(const char_type* __s1, const char_type* __s2, size_t __n)
646 {return __n == 0 ? 0 : memcmp(__s1, __s2, __n);}
647 static inline size_t length(const char_type* __s) {return strlen(__s);}
648 static inline const char_type* find(const char_type* __s, size_t __n, const char_type& __a)
649 {return __n == 0 ? NULL : (const char_type*) memchr(__s, to_int_type(__a), __n);}
650 static inline char_type* move(char_type* __s1, const char_type* __s2, size_t __n)
651 {return __n == 0 ? __s1 : (char_type*) memmove(__s1, __s2, __n);}
652 static inline char_type* copy(char_type* __s1, const char_type* __s2, size_t __n)
654 _LIBCPP_ASSERT(__s2 < __s1 || __s2 >= __s1+__n, "char_traits::copy overlapped range");
655 return __n == 0 ? __s1 : (char_type*)memcpy(__s1, __s2, __n);
657 static inline char_type* assign(char_type* __s, size_t __n, char_type __a)
658 {return __n == 0 ? __s : (char_type*)memset(__s, to_int_type(__a), __n);}
660 static inline _LIBCPP_CONSTEXPR int_type not_eof(int_type __c) _NOEXCEPT
661 {return eq_int_type(__c, eof()) ? ~eof() : __c;}
662 static inline _LIBCPP_CONSTEXPR char_type to_char_type(int_type __c) _NOEXCEPT
663 {return char_type(__c);}
664 static inline _LIBCPP_CONSTEXPR int_type to_int_type(char_type __c) _NOEXCEPT
665 {return int_type((unsigned char)__c);}
666 static inline _LIBCPP_CONSTEXPR bool eq_int_type(int_type __c1, int_type __c2) _NOEXCEPT
667 {return __c1 == __c2;}
668 static inline _LIBCPP_CONSTEXPR int_type eof() _NOEXCEPT
669 {return int_type(EOF);}
672 // char_traits<wchar_t>
675 struct _LIBCPP_TYPE_VIS_ONLY char_traits<wchar_t>
677 typedef wchar_t char_type;
678 typedef wint_t int_type;
679 typedef streamoff off_type;
680 typedef streampos pos_type;
681 typedef mbstate_t state_type;
683 static inline void assign(char_type& __c1, const char_type& __c2) _NOEXCEPT
685 static inline _LIBCPP_CONSTEXPR bool eq(char_type __c1, char_type __c2) _NOEXCEPT
686 {return __c1 == __c2;}
687 static inline _LIBCPP_CONSTEXPR bool lt(char_type __c1, char_type __c2) _NOEXCEPT
688 {return __c1 < __c2;}
690 static inline int compare(const char_type* __s1, const char_type* __s2, size_t __n)
691 {return __n == 0 ? 0 : wmemcmp(__s1, __s2, __n);}
692 static inline size_t length(const char_type* __s)
693 {return wcslen(__s);}
694 static inline const char_type* find(const char_type* __s, size_t __n, const char_type& __a)
695 {return __n == 0 ? NULL : (const char_type*)wmemchr(__s, __a, __n);}
696 static inline char_type* move(char_type* __s1, const char_type* __s2, size_t __n)
697 {return __n == 0 ? __s1 : (char_type*)wmemmove(__s1, __s2, __n);}
698 static inline char_type* copy(char_type* __s1, const char_type* __s2, size_t __n)
700 _LIBCPP_ASSERT(__s2 < __s1 || __s2 >= __s1+__n, "char_traits::copy overlapped range");
701 return __n == 0 ? __s1 : (char_type*)wmemcpy(__s1, __s2, __n);
703 static inline char_type* assign(char_type* __s, size_t __n, char_type __a)
704 {return __n == 0 ? __s : (char_type*)wmemset(__s, __a, __n);}
706 static inline _LIBCPP_CONSTEXPR int_type not_eof(int_type __c) _NOEXCEPT
707 {return eq_int_type(__c, eof()) ? ~eof() : __c;}
708 static inline _LIBCPP_CONSTEXPR char_type to_char_type(int_type __c) _NOEXCEPT
709 {return char_type(__c);}
710 static inline _LIBCPP_CONSTEXPR int_type to_int_type(char_type __c) _NOEXCEPT
711 {return int_type(__c);}
712 static inline _LIBCPP_CONSTEXPR bool eq_int_type(int_type __c1, int_type __c2) _NOEXCEPT
713 {return __c1 == __c2;}
714 static inline _LIBCPP_CONSTEXPR int_type eof() _NOEXCEPT
715 {return int_type(WEOF);}
718 #ifndef _LIBCPP_HAS_NO_UNICODE_CHARS
721 struct _LIBCPP_TYPE_VIS_ONLY char_traits<char16_t>
723 typedef char16_t char_type;
724 typedef uint_least16_t int_type;
725 typedef streamoff off_type;
726 typedef u16streampos pos_type;
727 typedef mbstate_t state_type;
729 static inline void assign(char_type& __c1, const char_type& __c2) _NOEXCEPT
731 static inline _LIBCPP_CONSTEXPR bool eq(char_type __c1, char_type __c2) _NOEXCEPT
732 {return __c1 == __c2;}
733 static inline _LIBCPP_CONSTEXPR bool lt(char_type __c1, char_type __c2) _NOEXCEPT
734 {return __c1 < __c2;}
736 _LIBCPP_INLINE_VISIBILITY
737 static int compare(const char_type* __s1, const char_type* __s2, size_t __n);
738 _LIBCPP_INLINE_VISIBILITY
739 static size_t length(const char_type* __s);
740 _LIBCPP_INLINE_VISIBILITY
741 static const char_type* find(const char_type* __s, size_t __n, const char_type& __a);
742 _LIBCPP_INLINE_VISIBILITY
743 static char_type* move(char_type* __s1, const char_type* __s2, size_t __n);
744 _LIBCPP_INLINE_VISIBILITY
745 static char_type* copy(char_type* __s1, const char_type* __s2, size_t __n);
746 _LIBCPP_INLINE_VISIBILITY
747 static char_type* assign(char_type* __s, size_t __n, char_type __a);
749 static inline _LIBCPP_CONSTEXPR int_type not_eof(int_type __c) _NOEXCEPT
750 {return eq_int_type(__c, eof()) ? ~eof() : __c;}
751 static inline _LIBCPP_CONSTEXPR char_type to_char_type(int_type __c) _NOEXCEPT
752 {return char_type(__c);}
753 static inline _LIBCPP_CONSTEXPR int_type to_int_type(char_type __c) _NOEXCEPT
754 {return int_type(__c);}
755 static inline _LIBCPP_CONSTEXPR bool eq_int_type(int_type __c1, int_type __c2) _NOEXCEPT
756 {return __c1 == __c2;}
757 static inline _LIBCPP_CONSTEXPR int_type eof() _NOEXCEPT
758 {return int_type(0xFFFF);}
763 char_traits<char16_t>::compare(const char_type* __s1, const char_type* __s2, size_t __n)
765 for (; __n; --__n, ++__s1, ++__s2)
767 if (lt(*__s1, *__s2))
769 if (lt(*__s2, *__s1))
777 char_traits<char16_t>::length(const char_type* __s)
780 for (; !eq(*__s, char_type(0)); ++__s)
787 char_traits<char16_t>::find(const char_type* __s, size_t __n, const char_type& __a)
800 char_traits<char16_t>::move(char_type* __s1, const char_type* __s2, size_t __n)
802 char_type* __r = __s1;
805 for (; __n; --__n, ++__s1, ++__s2)
806 assign(*__s1, *__s2);
808 else if (__s2 < __s1)
813 assign(*--__s1, *--__s2);
820 char_traits<char16_t>::copy(char_type* __s1, const char_type* __s2, size_t __n)
822 _LIBCPP_ASSERT(__s2 < __s1 || __s2 >= __s1+__n, "char_traits::copy overlapped range");
823 char_type* __r = __s1;
824 for (; __n; --__n, ++__s1, ++__s2)
825 assign(*__s1, *__s2);
831 char_traits<char16_t>::assign(char_type* __s, size_t __n, char_type __a)
833 char_type* __r = __s;
834 for (; __n; --__n, ++__s)
840 struct _LIBCPP_TYPE_VIS_ONLY char_traits<char32_t>
842 typedef char32_t char_type;
843 typedef uint_least32_t int_type;
844 typedef streamoff off_type;
845 typedef u32streampos pos_type;
846 typedef mbstate_t state_type;
848 static inline void assign(char_type& __c1, const char_type& __c2) _NOEXCEPT
850 static inline _LIBCPP_CONSTEXPR bool eq(char_type __c1, char_type __c2) _NOEXCEPT
851 {return __c1 == __c2;}
852 static inline _LIBCPP_CONSTEXPR bool lt(char_type __c1, char_type __c2) _NOEXCEPT
853 {return __c1 < __c2;}
855 _LIBCPP_INLINE_VISIBILITY
856 static int compare(const char_type* __s1, const char_type* __s2, size_t __n);
857 _LIBCPP_INLINE_VISIBILITY
858 static size_t length(const char_type* __s);
859 _LIBCPP_INLINE_VISIBILITY
860 static const char_type* find(const char_type* __s, size_t __n, const char_type& __a);
861 _LIBCPP_INLINE_VISIBILITY
862 static char_type* move(char_type* __s1, const char_type* __s2, size_t __n);
863 _LIBCPP_INLINE_VISIBILITY
864 static char_type* copy(char_type* __s1, const char_type* __s2, size_t __n);
865 _LIBCPP_INLINE_VISIBILITY
866 static char_type* assign(char_type* __s, size_t __n, char_type __a);
868 static inline _LIBCPP_CONSTEXPR int_type not_eof(int_type __c) _NOEXCEPT
869 {return eq_int_type(__c, eof()) ? ~eof() : __c;}
870 static inline _LIBCPP_CONSTEXPR char_type to_char_type(int_type __c) _NOEXCEPT
871 {return char_type(__c);}
872 static inline _LIBCPP_CONSTEXPR int_type to_int_type(char_type __c) _NOEXCEPT
873 {return int_type(__c);}
874 static inline _LIBCPP_CONSTEXPR bool eq_int_type(int_type __c1, int_type __c2) _NOEXCEPT
875 {return __c1 == __c2;}
876 static inline _LIBCPP_CONSTEXPR int_type eof() _NOEXCEPT
877 {return int_type(0xFFFFFFFF);}
882 char_traits<char32_t>::compare(const char_type* __s1, const char_type* __s2, size_t __n)
884 for (; __n; --__n, ++__s1, ++__s2)
886 if (lt(*__s1, *__s2))
888 if (lt(*__s2, *__s1))
896 char_traits<char32_t>::length(const char_type* __s)
899 for (; !eq(*__s, char_type(0)); ++__s)
906 char_traits<char32_t>::find(const char_type* __s, size_t __n, const char_type& __a)
919 char_traits<char32_t>::move(char_type* __s1, const char_type* __s2, size_t __n)
921 char_type* __r = __s1;
924 for (; __n; --__n, ++__s1, ++__s2)
925 assign(*__s1, *__s2);
927 else if (__s2 < __s1)
932 assign(*--__s1, *--__s2);
939 char_traits<char32_t>::copy(char_type* __s1, const char_type* __s2, size_t __n)
941 _LIBCPP_ASSERT(__s2 < __s1 || __s2 >= __s1+__n, "char_traits::copy overlapped range");
942 char_type* __r = __s1;
943 for (; __n; --__n, ++__s1, ++__s2)
944 assign(*__s1, *__s2);
950 char_traits<char32_t>::assign(char_type* __s, size_t __n, char_type __a)
952 char_type* __r = __s;
953 for (; __n; --__n, ++__s)
958 #endif // _LIBCPP_HAS_NO_UNICODE_CHARS
960 // helper fns for basic_string
963 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
964 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
965 __str_find(const _CharT *__p, _SizeT __sz,
966 _CharT __c, _SizeT __pos) _NOEXCEPT
970 const _CharT* __r = _Traits::find(__p + __pos, __sz - __pos, __c);
973 return static_cast<_SizeT>(__r - __p);
976 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
977 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
978 __str_find(const _CharT *__p, _SizeT __sz,
979 const _CharT* __s, _SizeT __pos, _SizeT __n) _NOEXCEPT
981 if (__pos > __sz || __sz - __pos < __n)
986 _VSTD::__search(__p + __pos, __p + __sz,
987 __s, __s + __n, _Traits::eq,
988 random_access_iterator_tag(), random_access_iterator_tag()).first;
989 if (__r == __p + __sz)
991 return static_cast<_SizeT>(__r - __p);
997 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
998 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
999 __str_rfind(const _CharT *__p, _SizeT __sz,
1000 _CharT __c, _SizeT __pos) _NOEXCEPT
1008 for (const _CharT* __ps = __p + __pos; __ps != __p;)
1010 if (_Traits::eq(*--__ps, __c))
1011 return static_cast<_SizeT>(__ps - __p);
1016 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
1017 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1018 __str_rfind(const _CharT *__p, _SizeT __sz,
1019 const _CharT* __s, _SizeT __pos, _SizeT __n) _NOEXCEPT
1021 __pos = _VSTD::min(__pos, __sz);
1022 if (__n < __sz - __pos)
1026 const _CharT* __r = _VSTD::__find_end(
1027 __p, __p + __pos, __s, __s + __n, _Traits::eq,
1028 random_access_iterator_tag(), random_access_iterator_tag());
1029 if (__n > 0 && __r == __p + __pos)
1031 return static_cast<_SizeT>(__r - __p);
1034 // __str_find_first_of
1035 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
1036 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1037 __str_find_first_of(const _CharT *__p, _SizeT __sz,
1038 const _CharT* __s, _SizeT __pos, _SizeT __n) _NOEXCEPT
1040 if (__pos >= __sz || __n == 0)
1042 const _CharT* __r = _VSTD::__find_first_of_ce
1043 (__p + __pos, __p + __sz, __s, __s + __n, _Traits::eq );
1044 if (__r == __p + __sz)
1046 return static_cast<_SizeT>(__r - __p);
1050 // __str_find_last_of
1051 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
1052 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1053 __str_find_last_of(const _CharT *__p, _SizeT __sz,
1054 const _CharT* __s, _SizeT __pos, _SizeT __n) _NOEXCEPT
1062 for (const _CharT* __ps = __p + __pos; __ps != __p;)
1064 const _CharT* __r = _Traits::find(__s, __n, *--__ps);
1066 return static_cast<_SizeT>(__ps - __p);
1073 // __str_find_first_not_of
1074 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
1075 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1076 __str_find_first_not_of(const _CharT *__p, _SizeT __sz,
1077 const _CharT* __s, _SizeT __pos, _SizeT __n) _NOEXCEPT
1081 const _CharT* __pe = __p + __sz;
1082 for (const _CharT* __ps = __p + __pos; __ps != __pe; ++__ps)
1083 if (_Traits::find(__s, __n, *__ps) == 0)
1084 return static_cast<_SizeT>(__ps - __p);
1090 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
1091 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1092 __str_find_first_not_of(const _CharT *__p, _SizeT __sz,
1093 _CharT __c, _SizeT __pos) _NOEXCEPT
1097 const _CharT* __pe = __p + __sz;
1098 for (const _CharT* __ps = __p + __pos; __ps != __pe; ++__ps)
1099 if (!_Traits::eq(*__ps, __c))
1100 return static_cast<_SizeT>(__ps - __p);
1106 // __str_find_last_not_of
1107 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
1108 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1109 __str_find_last_not_of(const _CharT *__p, _SizeT __sz,
1110 const _CharT* __s, _SizeT __pos, _SizeT __n) _NOEXCEPT
1116 for (const _CharT* __ps = __p + __pos; __ps != __p;)
1117 if (_Traits::find(__s, __n, *--__ps) == 0)
1118 return static_cast<_SizeT>(__ps - __p);
1123 template<class _CharT, class _SizeT, class _Traits, _SizeT __npos>
1124 inline _SizeT _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY
1125 __str_find_last_not_of(const _CharT *__p, _SizeT __sz,
1126 _CharT __c, _SizeT __pos) _NOEXCEPT
1132 for (const _CharT* __ps = __p + __pos; __ps != __p;)
1133 if (!_Traits::eq(*--__ps, __c))
1134 return static_cast<_SizeT>(__ps - __p);
1138 template<class _Ptr>
1139 size_t _LIBCPP_INLINE_VISIBILITY __do_string_hash(_Ptr __p, _Ptr __e)
1141 typedef typename iterator_traits<_Ptr>::value_type value_type;
1142 return __murmur2_or_cityhash<size_t>()(__p, (__e-__p)*sizeof(value_type));
1147 template<class _CharT, class _Traits, class _Allocator>
1148 basic_string<_CharT, _Traits, _Allocator>
1149 operator+(const basic_string<_CharT, _Traits, _Allocator>& __x,
1150 const basic_string<_CharT, _Traits, _Allocator>& __y);
1152 template<class _CharT, class _Traits, class _Allocator>
1153 basic_string<_CharT, _Traits, _Allocator>
1154 operator+(const _CharT* __x, const basic_string<_CharT,_Traits,_Allocator>& __y);
1156 template<class _CharT, class _Traits, class _Allocator>
1157 basic_string<_CharT, _Traits, _Allocator>
1158 operator+(_CharT __x, const basic_string<_CharT,_Traits,_Allocator>& __y);
1160 template<class _CharT, class _Traits, class _Allocator>
1161 basic_string<_CharT, _Traits, _Allocator>
1162 operator+(const basic_string<_CharT, _Traits, _Allocator>& __x, const _CharT* __y);
1164 template<class _CharT, class _Traits, class _Allocator>
1165 basic_string<_CharT, _Traits, _Allocator>
1166 operator+(const basic_string<_CharT, _Traits, _Allocator>& __x, _CharT __y);
1169 class _LIBCPP_TYPE_VIS_ONLY __basic_string_common
1172 void __throw_length_error() const;
1173 void __throw_out_of_range() const;
1178 __basic_string_common<__b>::__throw_length_error() const
1180 #ifndef _LIBCPP_NO_EXCEPTIONS
1181 throw length_error("basic_string");
1183 assert(!"basic_string length_error");
1189 __basic_string_common<__b>::__throw_out_of_range() const
1191 #ifndef _LIBCPP_NO_EXCEPTIONS
1192 throw out_of_range("basic_string");
1194 assert(!"basic_string out_of_range");
1199 #pragma warning( push )
1200 #pragma warning( disable: 4231 )
1201 #endif // _LIBCPP_MSVC
1202 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_TYPE_VIS __basic_string_common<true>)
1204 #pragma warning( pop )
1205 #endif // _LIBCPP_MSVC
1207 #ifdef _LIBCPP_NO_EXCEPTIONS
1208 template <class _Iter>
1209 struct __libcpp_string_gets_noexcept_iterator_impl : public true_type {};
1210 #elif defined(_LIBCPP_HAS_NO_NOEXCEPT)
1211 template <class _Iter>
1212 struct __libcpp_string_gets_noexcept_iterator_impl : public false_type {};
1214 template <class _Iter, bool = __is_forward_iterator<_Iter>::value>
1215 struct __libcpp_string_gets_noexcept_iterator_impl : public _LIBCPP_BOOL_CONSTANT((
1216 noexcept(++(declval<_Iter&>())) &&
1217 is_nothrow_assignable<_Iter&, _Iter>::value &&
1218 noexcept(declval<_Iter>() == declval<_Iter>()) &&
1219 noexcept(*declval<_Iter>())
1222 template <class _Iter>
1223 struct __libcpp_string_gets_noexcept_iterator_impl<_Iter, false> : public false_type {};
1227 template <class _Iter>
1228 struct __libcpp_string_gets_noexcept_iterator
1229 : public _LIBCPP_BOOL_CONSTANT(__libcpp_is_trivial_iterator<_Iter>::value || __libcpp_string_gets_noexcept_iterator_impl<_Iter>::value) {};
1231 #ifdef _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT
1233 template <class _CharT, size_t = sizeof(_CharT)>
1236 unsigned char __xx[sizeof(_CharT)-1];
1239 template <class _CharT>
1240 struct __padding<_CharT, 1>
1244 #endif // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT
1246 template<class _CharT, class _Traits, class _Allocator>
1247 class _LIBCPP_TYPE_VIS_ONLY basic_string
1248 : private __basic_string_common<true>
1251 typedef basic_string __self;
1252 typedef _Traits traits_type;
1253 typedef typename traits_type::char_type value_type;
1254 typedef _Allocator allocator_type;
1255 typedef allocator_traits<allocator_type> __alloc_traits;
1256 typedef typename __alloc_traits::size_type size_type;
1257 typedef typename __alloc_traits::difference_type difference_type;
1258 typedef value_type& reference;
1259 typedef const value_type& const_reference;
1260 typedef typename __alloc_traits::pointer pointer;
1261 typedef typename __alloc_traits::const_pointer const_pointer;
1263 static_assert(is_pod<value_type>::value, "Character type of basic_string must be a POD");
1264 static_assert((is_same<_CharT, value_type>::value),
1265 "traits_type::char_type must be the same type as CharT");
1266 static_assert((is_same<typename allocator_type::value_type, value_type>::value),
1267 "Allocator::value_type must be same type as value_type");
1268 #if defined(_LIBCPP_RAW_ITERATORS)
1269 typedef pointer iterator;
1270 typedef const_pointer const_iterator;
1271 #else // defined(_LIBCPP_RAW_ITERATORS)
1272 typedef __wrap_iter<pointer> iterator;
1273 typedef __wrap_iter<const_pointer> const_iterator;
1274 #endif // defined(_LIBCPP_RAW_ITERATORS)
1275 typedef _VSTD::reverse_iterator<iterator> reverse_iterator;
1276 typedef _VSTD::reverse_iterator<const_iterator> const_reverse_iterator;
1280 #ifdef _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT
1289 #if _LIBCPP_BIG_ENDIAN
1290 enum {__short_mask = 0x01};
1291 enum {__long_mask = 0x1ul};
1292 #else // _LIBCPP_BIG_ENDIAN
1293 enum {__short_mask = 0x80};
1294 enum {__long_mask = ~(size_type(~0) >> 1)};
1295 #endif // _LIBCPP_BIG_ENDIAN
1297 enum {__min_cap = (sizeof(__long) - 1)/sizeof(value_type) > 2 ?
1298 (sizeof(__long) - 1)/sizeof(value_type) : 2};
1302 value_type __data_[__min_cap];
1304 : __padding<value_type>
1306 unsigned char __size_;
1319 #if _LIBCPP_BIG_ENDIAN
1320 enum {__short_mask = 0x80};
1321 enum {__long_mask = ~(size_type(~0) >> 1)};
1322 #else // _LIBCPP_BIG_ENDIAN
1323 enum {__short_mask = 0x01};
1324 enum {__long_mask = 0x1ul};
1325 #endif // _LIBCPP_BIG_ENDIAN
1327 enum {__min_cap = (sizeof(__long) - 1)/sizeof(value_type) > 2 ?
1328 (sizeof(__long) - 1)/sizeof(value_type) : 2};
1334 unsigned char __size_;
1337 value_type __data_[__min_cap];
1340 #endif // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT
1342 union __ulx{__long __lx; __short __lxx;};
1344 enum {__n_words = sizeof(__ulx) / sizeof(size_type)};
1348 size_type __words[__n_words];
1361 __compressed_pair<__rep, allocator_type> __r_;
1364 static const size_type npos = -1;
1366 _LIBCPP_INLINE_VISIBILITY basic_string()
1367 _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value);
1369 _LIBCPP_INLINE_VISIBILITY explicit basic_string(const allocator_type& __a)
1370 #if _LIBCPP_STD_VER <= 14
1371 _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value);
1376 basic_string(const basic_string& __str);
1377 basic_string(const basic_string& __str, const allocator_type& __a);
1379 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
1380 _LIBCPP_INLINE_VISIBILITY
1381 basic_string(basic_string&& __str)
1382 #if _LIBCPP_STD_VER <= 14
1383 _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value);
1388 _LIBCPP_INLINE_VISIBILITY
1389 basic_string(basic_string&& __str, const allocator_type& __a);
1390 #endif // _LIBCPP_HAS_NO_RVALUE_REFERENCES
1391 _LIBCPP_INLINE_VISIBILITY basic_string(const value_type* __s);
1392 _LIBCPP_INLINE_VISIBILITY
1393 basic_string(const value_type* __s, const allocator_type& __a);
1394 _LIBCPP_INLINE_VISIBILITY
1395 basic_string(const value_type* __s, size_type __n);
1396 _LIBCPP_INLINE_VISIBILITY
1397 basic_string(const value_type* __s, size_type __n, const allocator_type& __a);
1398 _LIBCPP_INLINE_VISIBILITY
1399 basic_string(size_type __n, value_type __c);
1400 _LIBCPP_INLINE_VISIBILITY
1401 basic_string(size_type __n, value_type __c, const allocator_type& __a);
1402 basic_string(const basic_string& __str, size_type __pos, size_type __n,
1403 const allocator_type& __a = allocator_type());
1404 _LIBCPP_INLINE_VISIBILITY
1405 basic_string(const basic_string& __str, size_type __pos,
1406 const allocator_type& __a = allocator_type());
1407 template<class _InputIterator>
1408 _LIBCPP_INLINE_VISIBILITY
1409 basic_string(_InputIterator __first, _InputIterator __last);
1410 template<class _InputIterator>
1411 _LIBCPP_INLINE_VISIBILITY
1412 basic_string(_InputIterator __first, _InputIterator __last, const allocator_type& __a);
1413 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1414 _LIBCPP_INLINE_VISIBILITY
1415 basic_string(initializer_list<value_type> __il);
1416 _LIBCPP_INLINE_VISIBILITY
1417 basic_string(initializer_list<value_type> __il, const allocator_type& __a);
1418 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1422 basic_string& operator=(const basic_string& __str);
1423 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
1424 _LIBCPP_INLINE_VISIBILITY
1425 basic_string& operator=(basic_string&& __str)
1426 _NOEXCEPT_((__noexcept_move_assign_container<_Allocator, __alloc_traits>::value));
1428 _LIBCPP_INLINE_VISIBILITY basic_string& operator=(const value_type* __s) {return assign(__s);}
1429 basic_string& operator=(value_type __c);
1430 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1431 _LIBCPP_INLINE_VISIBILITY
1432 basic_string& operator=(initializer_list<value_type> __il) {return assign(__il.begin(), __il.size());}
1433 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1435 #if _LIBCPP_DEBUG_LEVEL >= 2
1436 _LIBCPP_INLINE_VISIBILITY
1437 iterator begin() _NOEXCEPT
1438 {return iterator(this, __get_pointer());}
1439 _LIBCPP_INLINE_VISIBILITY
1440 const_iterator begin() const _NOEXCEPT
1441 {return const_iterator(this, __get_pointer());}
1442 _LIBCPP_INLINE_VISIBILITY
1443 iterator end() _NOEXCEPT
1444 {return iterator(this, __get_pointer() + size());}
1445 _LIBCPP_INLINE_VISIBILITY
1446 const_iterator end() const _NOEXCEPT
1447 {return const_iterator(this, __get_pointer() + size());}
1449 _LIBCPP_INLINE_VISIBILITY
1450 iterator begin() _NOEXCEPT
1451 {return iterator(__get_pointer());}
1452 _LIBCPP_INLINE_VISIBILITY
1453 const_iterator begin() const _NOEXCEPT
1454 {return const_iterator(__get_pointer());}
1455 _LIBCPP_INLINE_VISIBILITY
1456 iterator end() _NOEXCEPT
1457 {return iterator(__get_pointer() + size());}
1458 _LIBCPP_INLINE_VISIBILITY
1459 const_iterator end() const _NOEXCEPT
1460 {return const_iterator(__get_pointer() + size());}
1461 #endif // _LIBCPP_DEBUG_LEVEL >= 2
1462 _LIBCPP_INLINE_VISIBILITY
1463 reverse_iterator rbegin() _NOEXCEPT
1464 {return reverse_iterator(end());}
1465 _LIBCPP_INLINE_VISIBILITY
1466 const_reverse_iterator rbegin() const _NOEXCEPT
1467 {return const_reverse_iterator(end());}
1468 _LIBCPP_INLINE_VISIBILITY
1469 reverse_iterator rend() _NOEXCEPT
1470 {return reverse_iterator(begin());}
1471 _LIBCPP_INLINE_VISIBILITY
1472 const_reverse_iterator rend() const _NOEXCEPT
1473 {return const_reverse_iterator(begin());}
1475 _LIBCPP_INLINE_VISIBILITY
1476 const_iterator cbegin() const _NOEXCEPT
1478 _LIBCPP_INLINE_VISIBILITY
1479 const_iterator cend() const _NOEXCEPT
1481 _LIBCPP_INLINE_VISIBILITY
1482 const_reverse_iterator crbegin() const _NOEXCEPT
1484 _LIBCPP_INLINE_VISIBILITY
1485 const_reverse_iterator crend() const _NOEXCEPT
1488 _LIBCPP_INLINE_VISIBILITY size_type size() const _NOEXCEPT
1489 {return __is_long() ? __get_long_size() : __get_short_size();}
1490 _LIBCPP_INLINE_VISIBILITY size_type length() const _NOEXCEPT {return size();}
1491 _LIBCPP_INLINE_VISIBILITY size_type max_size() const _NOEXCEPT;
1492 _LIBCPP_INLINE_VISIBILITY size_type capacity() const _NOEXCEPT
1493 {return (__is_long() ? __get_long_cap()
1494 : static_cast<size_type>(__min_cap)) - 1;}
1496 void resize(size_type __n, value_type __c);
1497 _LIBCPP_INLINE_VISIBILITY void resize(size_type __n) {resize(__n, value_type());}
1499 void reserve(size_type res_arg = 0);
1500 _LIBCPP_INLINE_VISIBILITY
1501 void shrink_to_fit() _NOEXCEPT {reserve();}
1502 _LIBCPP_INLINE_VISIBILITY
1503 void clear() _NOEXCEPT;
1504 _LIBCPP_INLINE_VISIBILITY bool empty() const _NOEXCEPT {return size() == 0;}
1506 _LIBCPP_INLINE_VISIBILITY const_reference operator[](size_type __pos) const;
1507 _LIBCPP_INLINE_VISIBILITY reference operator[](size_type __pos);
1509 const_reference at(size_type __n) const;
1510 reference at(size_type __n);
1512 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(const basic_string& __str) {return append(__str);}
1513 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(const value_type* __s) {return append(__s);}
1514 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(value_type __c) {push_back(__c); return *this;}
1515 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1516 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(initializer_list<value_type> __il) {return append(__il);}
1517 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1519 _LIBCPP_INLINE_VISIBILITY
1520 basic_string& append(const basic_string& __str);
1521 basic_string& append(const basic_string& __str, size_type __pos, size_type __n=npos);
1522 basic_string& append(const value_type* __s, size_type __n);
1523 basic_string& append(const value_type* __s);
1524 basic_string& append(size_type __n, value_type __c);
1525 template<class _InputIterator>
1528 __is_exactly_input_iterator<_InputIterator>::value
1529 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value,
1532 append(_InputIterator __first, _InputIterator __last);
1533 template<class _ForwardIterator>
1536 __is_forward_iterator<_ForwardIterator>::value
1537 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value,
1540 append(_ForwardIterator __first, _ForwardIterator __last);
1541 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1542 _LIBCPP_INLINE_VISIBILITY
1543 basic_string& append(initializer_list<value_type> __il) {return append(__il.begin(), __il.size());}
1544 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1546 void push_back(value_type __c);
1547 _LIBCPP_INLINE_VISIBILITY
1549 _LIBCPP_INLINE_VISIBILITY reference front();
1550 _LIBCPP_INLINE_VISIBILITY const_reference front() const;
1551 _LIBCPP_INLINE_VISIBILITY reference back();
1552 _LIBCPP_INLINE_VISIBILITY const_reference back() const;
1554 _LIBCPP_INLINE_VISIBILITY
1555 basic_string& assign(const basic_string& __str) { return *this = __str; }
1556 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
1557 _LIBCPP_INLINE_VISIBILITY
1558 basic_string& assign(basic_string&& str)
1559 _NOEXCEPT_((__noexcept_move_assign_container<_Allocator, __alloc_traits>::value))
1560 {*this = _VSTD::move(str); return *this;}
1562 basic_string& assign(const basic_string& __str, size_type __pos, size_type __n=npos);
1563 basic_string& assign(const value_type* __s, size_type __n);
1564 basic_string& assign(const value_type* __s);
1565 basic_string& assign(size_type __n, value_type __c);
1566 template<class _InputIterator>
1569 __is_exactly_input_iterator<_InputIterator>::value
1570 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value,
1573 assign(_InputIterator __first, _InputIterator __last);
1574 template<class _ForwardIterator>
1577 __is_forward_iterator<_ForwardIterator>::value
1578 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value,
1581 assign(_ForwardIterator __first, _ForwardIterator __last);
1582 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1583 _LIBCPP_INLINE_VISIBILITY
1584 basic_string& assign(initializer_list<value_type> __il) {return assign(__il.begin(), __il.size());}
1585 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1587 _LIBCPP_INLINE_VISIBILITY
1588 basic_string& insert(size_type __pos1, const basic_string& __str);
1589 basic_string& insert(size_type __pos1, const basic_string& __str, size_type __pos2, size_type __n=npos);
1590 basic_string& insert(size_type __pos, const value_type* __s, size_type __n);
1591 basic_string& insert(size_type __pos, const value_type* __s);
1592 basic_string& insert(size_type __pos, size_type __n, value_type __c);
1593 iterator insert(const_iterator __pos, value_type __c);
1594 _LIBCPP_INLINE_VISIBILITY
1595 iterator insert(const_iterator __pos, size_type __n, value_type __c);
1596 template<class _InputIterator>
1599 __is_exactly_input_iterator<_InputIterator>::value
1600 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value,
1603 insert(const_iterator __pos, _InputIterator __first, _InputIterator __last);
1604 template<class _ForwardIterator>
1607 __is_forward_iterator<_ForwardIterator>::value
1608 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value,
1611 insert(const_iterator __pos, _ForwardIterator __first, _ForwardIterator __last);
1612 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1613 _LIBCPP_INLINE_VISIBILITY
1614 iterator insert(const_iterator __pos, initializer_list<value_type> __il)
1615 {return insert(__pos, __il.begin(), __il.end());}
1616 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1618 basic_string& erase(size_type __pos = 0, size_type __n = npos);
1619 _LIBCPP_INLINE_VISIBILITY
1620 iterator erase(const_iterator __pos);
1621 _LIBCPP_INLINE_VISIBILITY
1622 iterator erase(const_iterator __first, const_iterator __last);
1624 _LIBCPP_INLINE_VISIBILITY
1625 basic_string& replace(size_type __pos1, size_type __n1, const basic_string& __str);
1626 basic_string& replace(size_type __pos1, size_type __n1, const basic_string& __str, size_type __pos2, size_type __n2=npos);
1627 basic_string& replace(size_type __pos, size_type __n1, const value_type* __s, size_type __n2);
1628 basic_string& replace(size_type __pos, size_type __n1, const value_type* __s);
1629 basic_string& replace(size_type __pos, size_type __n1, size_type __n2, value_type __c);
1630 _LIBCPP_INLINE_VISIBILITY
1631 basic_string& replace(const_iterator __i1, const_iterator __i2, const basic_string& __str);
1632 _LIBCPP_INLINE_VISIBILITY
1633 basic_string& replace(const_iterator __i1, const_iterator __i2, const value_type* __s, size_type __n);
1634 _LIBCPP_INLINE_VISIBILITY
1635 basic_string& replace(const_iterator __i1, const_iterator __i2, const value_type* __s);
1636 _LIBCPP_INLINE_VISIBILITY
1637 basic_string& replace(const_iterator __i1, const_iterator __i2, size_type __n, value_type __c);
1638 template<class _InputIterator>
1641 __is_input_iterator<_InputIterator>::value,
1644 replace(const_iterator __i1, const_iterator __i2, _InputIterator __j1, _InputIterator __j2);
1645 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1646 _LIBCPP_INLINE_VISIBILITY
1647 basic_string& replace(const_iterator __i1, const_iterator __i2, initializer_list<value_type> __il)
1648 {return replace(__i1, __i2, __il.begin(), __il.end());}
1649 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
1651 size_type copy(value_type* __s, size_type __n, size_type __pos = 0) const;
1652 _LIBCPP_INLINE_VISIBILITY
1653 basic_string substr(size_type __pos = 0, size_type __n = npos) const;
1655 _LIBCPP_INLINE_VISIBILITY
1656 void swap(basic_string& __str)
1657 #if _LIBCPP_STD_VER >= 14
1660 _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
1661 __is_nothrow_swappable<allocator_type>::value);
1664 _LIBCPP_INLINE_VISIBILITY
1665 const value_type* c_str() const _NOEXCEPT {return data();}
1666 _LIBCPP_INLINE_VISIBILITY
1667 const value_type* data() const _NOEXCEPT {return _VSTD::__to_raw_pointer(__get_pointer());}
1668 #if _LIBCPP_STD_VER > 14
1669 _LIBCPP_INLINE_VISIBILITY
1670 value_type* data() _NOEXCEPT {return _VSTD::__to_raw_pointer(__get_pointer());}
1673 _LIBCPP_INLINE_VISIBILITY
1674 allocator_type get_allocator() const _NOEXCEPT {return __alloc();}
1676 _LIBCPP_INLINE_VISIBILITY
1677 size_type find(const basic_string& __str, size_type __pos = 0) const _NOEXCEPT;
1678 size_type find(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT;
1679 _LIBCPP_INLINE_VISIBILITY
1680 size_type find(const value_type* __s, size_type __pos = 0) const _NOEXCEPT;
1681 size_type find(value_type __c, size_type __pos = 0) const _NOEXCEPT;
1683 _LIBCPP_INLINE_VISIBILITY
1684 size_type rfind(const basic_string& __str, size_type __pos = npos) const _NOEXCEPT;
1685 size_type rfind(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT;
1686 _LIBCPP_INLINE_VISIBILITY
1687 size_type rfind(const value_type* __s, size_type __pos = npos) const _NOEXCEPT;
1688 size_type rfind(value_type __c, size_type __pos = npos) const _NOEXCEPT;
1690 _LIBCPP_INLINE_VISIBILITY
1691 size_type find_first_of(const basic_string& __str, size_type __pos = 0) const _NOEXCEPT;
1692 size_type find_first_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT;
1693 _LIBCPP_INLINE_VISIBILITY
1694 size_type find_first_of(const value_type* __s, size_type __pos = 0) const _NOEXCEPT;
1695 _LIBCPP_INLINE_VISIBILITY
1696 size_type find_first_of(value_type __c, size_type __pos = 0) const _NOEXCEPT;
1698 _LIBCPP_INLINE_VISIBILITY
1699 size_type find_last_of(const basic_string& __str, size_type __pos = npos) const _NOEXCEPT;
1700 size_type find_last_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT;
1701 _LIBCPP_INLINE_VISIBILITY
1702 size_type find_last_of(const value_type* __s, size_type __pos = npos) const _NOEXCEPT;
1703 _LIBCPP_INLINE_VISIBILITY
1704 size_type find_last_of(value_type __c, size_type __pos = npos) const _NOEXCEPT;
1706 _LIBCPP_INLINE_VISIBILITY
1707 size_type find_first_not_of(const basic_string& __str, size_type __pos = 0) const _NOEXCEPT;
1708 size_type find_first_not_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT;
1709 _LIBCPP_INLINE_VISIBILITY
1710 size_type find_first_not_of(const value_type* __s, size_type __pos = 0) const _NOEXCEPT;
1711 _LIBCPP_INLINE_VISIBILITY
1712 size_type find_first_not_of(value_type __c, size_type __pos = 0) const _NOEXCEPT;
1714 _LIBCPP_INLINE_VISIBILITY
1715 size_type find_last_not_of(const basic_string& __str, size_type __pos = npos) const _NOEXCEPT;
1716 size_type find_last_not_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT;
1717 _LIBCPP_INLINE_VISIBILITY
1718 size_type find_last_not_of(const value_type* __s, size_type __pos = npos) const _NOEXCEPT;
1719 _LIBCPP_INLINE_VISIBILITY
1720 size_type find_last_not_of(value_type __c, size_type __pos = npos) const _NOEXCEPT;
1722 _LIBCPP_INLINE_VISIBILITY
1723 int compare(const basic_string& __str) const _NOEXCEPT;
1724 _LIBCPP_INLINE_VISIBILITY
1725 int compare(size_type __pos1, size_type __n1, const basic_string& __str) const;
1726 int compare(size_type __pos1, size_type __n1, const basic_string& __str, size_type __pos2, size_type __n2=npos) const;
1727 int compare(const value_type* __s) const _NOEXCEPT;
1728 int compare(size_type __pos1, size_type __n1, const value_type* __s) const;
1729 int compare(size_type __pos1, size_type __n1, const value_type* __s, size_type __n2) const;
1731 _LIBCPP_INLINE_VISIBILITY bool __invariants() const;
1733 _LIBCPP_INLINE_VISIBILITY
1734 bool __is_long() const _NOEXCEPT
1735 {return bool(__r_.first().__s.__size_ & __short_mask);}
1737 #if _LIBCPP_DEBUG_LEVEL >= 2
1739 bool __dereferenceable(const const_iterator* __i) const;
1740 bool __decrementable(const const_iterator* __i) const;
1741 bool __addable(const const_iterator* __i, ptrdiff_t __n) const;
1742 bool __subscriptable(const const_iterator* __i, ptrdiff_t __n) const;
1744 #endif // _LIBCPP_DEBUG_LEVEL >= 2
1747 _LIBCPP_INLINE_VISIBILITY
1748 allocator_type& __alloc() _NOEXCEPT
1749 {return __r_.second();}
1750 _LIBCPP_INLINE_VISIBILITY
1751 const allocator_type& __alloc() const _NOEXCEPT
1752 {return __r_.second();}
1754 #ifdef _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT
1756 _LIBCPP_INLINE_VISIBILITY
1757 void __set_short_size(size_type __s) _NOEXCEPT
1758 # if _LIBCPP_BIG_ENDIAN
1759 {__r_.first().__s.__size_ = (unsigned char)(__s << 1);}
1761 {__r_.first().__s.__size_ = (unsigned char)(__s);}
1764 _LIBCPP_INLINE_VISIBILITY
1765 size_type __get_short_size() const _NOEXCEPT
1766 # if _LIBCPP_BIG_ENDIAN
1767 {return __r_.first().__s.__size_ >> 1;}
1769 {return __r_.first().__s.__size_;}
1772 #else // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT
1774 _LIBCPP_INLINE_VISIBILITY
1775 void __set_short_size(size_type __s) _NOEXCEPT
1776 # if _LIBCPP_BIG_ENDIAN
1777 {__r_.first().__s.__size_ = (unsigned char)(__s);}
1779 {__r_.first().__s.__size_ = (unsigned char)(__s << 1);}
1782 _LIBCPP_INLINE_VISIBILITY
1783 size_type __get_short_size() const _NOEXCEPT
1784 # if _LIBCPP_BIG_ENDIAN
1785 {return __r_.first().__s.__size_;}
1787 {return __r_.first().__s.__size_ >> 1;}
1790 #endif // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT
1792 _LIBCPP_INLINE_VISIBILITY
1793 void __set_long_size(size_type __s) _NOEXCEPT
1794 {__r_.first().__l.__size_ = __s;}
1795 _LIBCPP_INLINE_VISIBILITY
1796 size_type __get_long_size() const _NOEXCEPT
1797 {return __r_.first().__l.__size_;}
1798 _LIBCPP_INLINE_VISIBILITY
1799 void __set_size(size_type __s) _NOEXCEPT
1800 {if (__is_long()) __set_long_size(__s); else __set_short_size(__s);}
1802 _LIBCPP_INLINE_VISIBILITY
1803 void __set_long_cap(size_type __s) _NOEXCEPT
1804 {__r_.first().__l.__cap_ = __long_mask | __s;}
1805 _LIBCPP_INLINE_VISIBILITY
1806 size_type __get_long_cap() const _NOEXCEPT
1807 {return __r_.first().__l.__cap_ & size_type(~__long_mask);}
1809 _LIBCPP_INLINE_VISIBILITY
1810 void __set_long_pointer(pointer __p) _NOEXCEPT
1811 {__r_.first().__l.__data_ = __p;}
1812 _LIBCPP_INLINE_VISIBILITY
1813 pointer __get_long_pointer() _NOEXCEPT
1814 {return __r_.first().__l.__data_;}
1815 _LIBCPP_INLINE_VISIBILITY
1816 const_pointer __get_long_pointer() const _NOEXCEPT
1817 {return __r_.first().__l.__data_;}
1818 _LIBCPP_INLINE_VISIBILITY
1819 pointer __get_short_pointer() _NOEXCEPT
1820 {return pointer_traits<pointer>::pointer_to(__r_.first().__s.__data_[0]);}
1821 _LIBCPP_INLINE_VISIBILITY
1822 const_pointer __get_short_pointer() const _NOEXCEPT
1823 {return pointer_traits<const_pointer>::pointer_to(__r_.first().__s.__data_[0]);}
1824 _LIBCPP_INLINE_VISIBILITY
1825 pointer __get_pointer() _NOEXCEPT
1826 {return __is_long() ? __get_long_pointer() : __get_short_pointer();}
1827 _LIBCPP_INLINE_VISIBILITY
1828 const_pointer __get_pointer() const _NOEXCEPT
1829 {return __is_long() ? __get_long_pointer() : __get_short_pointer();}
1831 _LIBCPP_INLINE_VISIBILITY
1832 void __zero() _NOEXCEPT
1834 size_type (&__a)[__n_words] = __r_.first().__r.__words;
1835 for (unsigned __i = 0; __i < __n_words; ++__i)
1839 template <size_type __a> static
1840 _LIBCPP_INLINE_VISIBILITY
1841 size_type __align_it(size_type __s) _NOEXCEPT
1842 {return (__s + (__a-1)) & ~(__a-1);}
1843 enum {__alignment = 16};
1844 static _LIBCPP_INLINE_VISIBILITY
1845 size_type __recommend(size_type __s) _NOEXCEPT
1846 {return (__s < __min_cap ? static_cast<size_type>(__min_cap) :
1847 __align_it<sizeof(value_type) < __alignment ?
1848 __alignment/sizeof(value_type) : 1 > (__s+1)) - 1;}
1850 void __init(const value_type* __s, size_type __sz, size_type __reserve);
1851 void __init(const value_type* __s, size_type __sz);
1852 void __init(size_type __n, value_type __c);
1854 template <class _InputIterator>
1857 __is_exactly_input_iterator<_InputIterator>::value,
1860 __init(_InputIterator __first, _InputIterator __last);
1862 template <class _ForwardIterator>
1865 __is_forward_iterator<_ForwardIterator>::value,
1868 __init(_ForwardIterator __first, _ForwardIterator __last);
1870 void __grow_by(size_type __old_cap, size_type __delta_cap, size_type __old_sz,
1871 size_type __n_copy, size_type __n_del, size_type __n_add = 0);
1872 void __grow_by_and_replace(size_type __old_cap, size_type __delta_cap, size_type __old_sz,
1873 size_type __n_copy, size_type __n_del,
1874 size_type __n_add, const value_type* __p_new_stuff);
1876 _LIBCPP_INLINE_VISIBILITY
1877 void __erase_to_end(size_type __pos);
1879 _LIBCPP_INLINE_VISIBILITY
1880 void __copy_assign_alloc(const basic_string& __str)
1881 {__copy_assign_alloc(__str, integral_constant<bool,
1882 __alloc_traits::propagate_on_container_copy_assignment::value>());}
1884 _LIBCPP_INLINE_VISIBILITY
1885 void __copy_assign_alloc(const basic_string& __str, true_type)
1887 if (__alloc() != __str.__alloc())
1892 __alloc() = __str.__alloc();
1895 _LIBCPP_INLINE_VISIBILITY
1896 void __copy_assign_alloc(const basic_string&, false_type) _NOEXCEPT
1899 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
1900 _LIBCPP_INLINE_VISIBILITY
1901 void __move_assign(basic_string& __str, false_type)
1902 _NOEXCEPT_(__alloc_traits::is_always_equal::value);
1903 _LIBCPP_INLINE_VISIBILITY
1904 void __move_assign(basic_string& __str, true_type)
1905 #if _LIBCPP_STD_VER > 14
1908 _NOEXCEPT_(is_nothrow_move_assignable<allocator_type>::value);
1912 _LIBCPP_INLINE_VISIBILITY
1914 __move_assign_alloc(basic_string& __str)
1916 !__alloc_traits::propagate_on_container_move_assignment::value ||
1917 is_nothrow_move_assignable<allocator_type>::value)
1918 {__move_assign_alloc(__str, integral_constant<bool,
1919 __alloc_traits::propagate_on_container_move_assignment::value>());}
1921 _LIBCPP_INLINE_VISIBILITY
1922 void __move_assign_alloc(basic_string& __c, true_type)
1923 _NOEXCEPT_(is_nothrow_move_assignable<allocator_type>::value)
1925 __alloc() = _VSTD::move(__c.__alloc());
1928 _LIBCPP_INLINE_VISIBILITY
1929 void __move_assign_alloc(basic_string&, false_type)
1933 _LIBCPP_INLINE_VISIBILITY void __invalidate_all_iterators();
1934 _LIBCPP_INLINE_VISIBILITY void __invalidate_iterators_past(size_type);
1936 friend basic_string operator+<>(const basic_string&, const basic_string&);
1937 friend basic_string operator+<>(const value_type*, const basic_string&);
1938 friend basic_string operator+<>(value_type, const basic_string&);
1939 friend basic_string operator+<>(const basic_string&, const value_type*);
1940 friend basic_string operator+<>(const basic_string&, value_type);
1943 template <class _CharT, class _Traits, class _Allocator>
1944 inline _LIBCPP_INLINE_VISIBILITY
1946 basic_string<_CharT, _Traits, _Allocator>::__invalidate_all_iterators()
1948 #if _LIBCPP_DEBUG_LEVEL >= 2
1949 __get_db()->__invalidate_all(this);
1950 #endif // _LIBCPP_DEBUG_LEVEL >= 2
1953 template <class _CharT, class _Traits, class _Allocator>
1954 inline _LIBCPP_INLINE_VISIBILITY
1956 basic_string<_CharT, _Traits, _Allocator>::__invalidate_iterators_past(size_type
1957 #if _LIBCPP_DEBUG_LEVEL >= 2
1962 #if _LIBCPP_DEBUG_LEVEL >= 2
1963 __c_node* __c = __get_db()->__find_c_and_lock(this);
1966 const_pointer __new_last = __get_pointer() + __pos;
1967 for (__i_node** __p = __c->end_; __p != __c->beg_; )
1970 const_iterator* __i = static_cast<const_iterator*>((*__p)->__i_);
1971 if (__i->base() > __new_last)
1973 (*__p)->__c_ = nullptr;
1974 if (--__c->end_ != __p)
1975 memmove(__p, __p+1, (__c->end_ - __p)*sizeof(__i_node*));
1978 __get_db()->unlock();
1980 #endif // _LIBCPP_DEBUG_LEVEL >= 2
1983 template <class _CharT, class _Traits, class _Allocator>
1984 inline _LIBCPP_INLINE_VISIBILITY
1985 basic_string<_CharT, _Traits, _Allocator>::basic_string()
1986 _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value)
1988 #if _LIBCPP_DEBUG_LEVEL >= 2
1989 __get_db()->__insert_c(this);
1994 template <class _CharT, class _Traits, class _Allocator>
1995 inline _LIBCPP_INLINE_VISIBILITY
1996 basic_string<_CharT, _Traits, _Allocator>::basic_string(const allocator_type& __a)
1997 #if _LIBCPP_STD_VER <= 14
1998 _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value)
2004 #if _LIBCPP_DEBUG_LEVEL >= 2
2005 __get_db()->__insert_c(this);
2010 template <class _CharT, class _Traits, class _Allocator>
2012 basic_string<_CharT, _Traits, _Allocator>::__init(const value_type* __s, size_type __sz, size_type __reserve)
2014 if (__reserve > max_size())
2015 this->__throw_length_error();
2017 if (__reserve < __min_cap)
2019 __set_short_size(__sz);
2020 __p = __get_short_pointer();
2024 size_type __cap = __recommend(__reserve);
2025 __p = __alloc_traits::allocate(__alloc(), __cap+1);
2026 __set_long_pointer(__p);
2027 __set_long_cap(__cap+1);
2028 __set_long_size(__sz);
2030 traits_type::copy(_VSTD::__to_raw_pointer(__p), __s, __sz);
2031 traits_type::assign(__p[__sz], value_type());
2034 template <class _CharT, class _Traits, class _Allocator>
2036 basic_string<_CharT, _Traits, _Allocator>::__init(const value_type* __s, size_type __sz)
2038 if (__sz > max_size())
2039 this->__throw_length_error();
2041 if (__sz < __min_cap)
2043 __set_short_size(__sz);
2044 __p = __get_short_pointer();
2048 size_type __cap = __recommend(__sz);
2049 __p = __alloc_traits::allocate(__alloc(), __cap+1);
2050 __set_long_pointer(__p);
2051 __set_long_cap(__cap+1);
2052 __set_long_size(__sz);
2054 traits_type::copy(_VSTD::__to_raw_pointer(__p), __s, __sz);
2055 traits_type::assign(__p[__sz], value_type());
2058 template <class _CharT, class _Traits, class _Allocator>
2059 inline _LIBCPP_INLINE_VISIBILITY
2060 basic_string<_CharT, _Traits, _Allocator>::basic_string(const value_type* __s)
2062 _LIBCPP_ASSERT(__s != nullptr, "basic_string(const char*) detected nullptr");
2063 __init(__s, traits_type::length(__s));
2064 #if _LIBCPP_DEBUG_LEVEL >= 2
2065 __get_db()->__insert_c(this);
2069 template <class _CharT, class _Traits, class _Allocator>
2070 inline _LIBCPP_INLINE_VISIBILITY
2071 basic_string<_CharT, _Traits, _Allocator>::basic_string(const value_type* __s, const allocator_type& __a)
2074 _LIBCPP_ASSERT(__s != nullptr, "basic_string(const char*, allocator) detected nullptr");
2075 __init(__s, traits_type::length(__s));
2076 #if _LIBCPP_DEBUG_LEVEL >= 2
2077 __get_db()->__insert_c(this);
2081 template <class _CharT, class _Traits, class _Allocator>
2082 inline _LIBCPP_INLINE_VISIBILITY
2083 basic_string<_CharT, _Traits, _Allocator>::basic_string(const value_type* __s, size_type __n)
2085 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "basic_string(const char*, n) detected nullptr");
2087 #if _LIBCPP_DEBUG_LEVEL >= 2
2088 __get_db()->__insert_c(this);
2092 template <class _CharT, class _Traits, class _Allocator>
2093 inline _LIBCPP_INLINE_VISIBILITY
2094 basic_string<_CharT, _Traits, _Allocator>::basic_string(const value_type* __s, size_type __n, const allocator_type& __a)
2097 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "basic_string(const char*, n, allocator) detected nullptr");
2099 #if _LIBCPP_DEBUG_LEVEL >= 2
2100 __get_db()->__insert_c(this);
2104 template <class _CharT, class _Traits, class _Allocator>
2105 basic_string<_CharT, _Traits, _Allocator>::basic_string(const basic_string& __str)
2106 : __r_(__alloc_traits::select_on_container_copy_construction(__str.__alloc()))
2108 if (!__str.__is_long())
2109 __r_.first().__r = __str.__r_.first().__r;
2111 __init(_VSTD::__to_raw_pointer(__str.__get_long_pointer()), __str.__get_long_size());
2112 #if _LIBCPP_DEBUG_LEVEL >= 2
2113 __get_db()->__insert_c(this);
2117 template <class _CharT, class _Traits, class _Allocator>
2118 basic_string<_CharT, _Traits, _Allocator>::basic_string(const basic_string& __str, const allocator_type& __a)
2121 if (!__str.__is_long())
2122 __r_.first().__r = __str.__r_.first().__r;
2124 __init(_VSTD::__to_raw_pointer(__str.__get_long_pointer()), __str.__get_long_size());
2125 #if _LIBCPP_DEBUG_LEVEL >= 2
2126 __get_db()->__insert_c(this);
2130 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
2132 template <class _CharT, class _Traits, class _Allocator>
2133 inline _LIBCPP_INLINE_VISIBILITY
2134 basic_string<_CharT, _Traits, _Allocator>::basic_string(basic_string&& __str)
2135 #if _LIBCPP_STD_VER <= 14
2136 _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value)
2140 : __r_(_VSTD::move(__str.__r_))
2143 #if _LIBCPP_DEBUG_LEVEL >= 2
2144 __get_db()->__insert_c(this);
2146 __get_db()->swap(this, &__str);
2150 template <class _CharT, class _Traits, class _Allocator>
2151 inline _LIBCPP_INLINE_VISIBILITY
2152 basic_string<_CharT, _Traits, _Allocator>::basic_string(basic_string&& __str, const allocator_type& __a)
2155 if (__str.__is_long() && __a != __str.__alloc()) // copy, not move
2156 __init(_VSTD::__to_raw_pointer(__str.__get_long_pointer()), __str.__get_long_size());
2159 __r_.first().__r = __str.__r_.first().__r;
2162 #if _LIBCPP_DEBUG_LEVEL >= 2
2163 __get_db()->__insert_c(this);
2165 __get_db()->swap(this, &__str);
2169 #endif // _LIBCPP_HAS_NO_RVALUE_REFERENCES
2171 template <class _CharT, class _Traits, class _Allocator>
2173 basic_string<_CharT, _Traits, _Allocator>::__init(size_type __n, value_type __c)
2175 if (__n > max_size())
2176 this->__throw_length_error();
2178 if (__n < __min_cap)
2180 __set_short_size(__n);
2181 __p = __get_short_pointer();
2185 size_type __cap = __recommend(__n);
2186 __p = __alloc_traits::allocate(__alloc(), __cap+1);
2187 __set_long_pointer(__p);
2188 __set_long_cap(__cap+1);
2189 __set_long_size(__n);
2191 traits_type::assign(_VSTD::__to_raw_pointer(__p), __n, __c);
2192 traits_type::assign(__p[__n], value_type());
2195 template <class _CharT, class _Traits, class _Allocator>
2196 inline _LIBCPP_INLINE_VISIBILITY
2197 basic_string<_CharT, _Traits, _Allocator>::basic_string(size_type __n, value_type __c)
2200 #if _LIBCPP_DEBUG_LEVEL >= 2
2201 __get_db()->__insert_c(this);
2205 template <class _CharT, class _Traits, class _Allocator>
2206 inline _LIBCPP_INLINE_VISIBILITY
2207 basic_string<_CharT, _Traits, _Allocator>::basic_string(size_type __n, value_type __c, const allocator_type& __a)
2211 #if _LIBCPP_DEBUG_LEVEL >= 2
2212 __get_db()->__insert_c(this);
2216 template <class _CharT, class _Traits, class _Allocator>
2217 basic_string<_CharT, _Traits, _Allocator>::basic_string(const basic_string& __str, size_type __pos, size_type __n,
2218 const allocator_type& __a)
2221 size_type __str_sz = __str.size();
2222 if (__pos > __str_sz)
2223 this->__throw_out_of_range();
2224 __init(__str.data() + __pos, _VSTD::min(__n, __str_sz - __pos));
2225 #if _LIBCPP_DEBUG_LEVEL >= 2
2226 __get_db()->__insert_c(this);
2230 template <class _CharT, class _Traits, class _Allocator>
2231 inline _LIBCPP_INLINE_VISIBILITY
2232 basic_string<_CharT, _Traits, _Allocator>::basic_string(const basic_string& __str, size_type __pos,
2233 const allocator_type& __a)
2236 size_type __str_sz = __str.size();
2237 if (__pos > __str_sz)
2238 this->__throw_out_of_range();
2239 __init(__str.data() + __pos, __str_sz - __pos);
2240 #if _LIBCPP_DEBUG_LEVEL >= 2
2241 __get_db()->__insert_c(this);
2245 template <class _CharT, class _Traits, class _Allocator>
2246 template <class _InputIterator>
2249 __is_exactly_input_iterator<_InputIterator>::value,
2252 basic_string<_CharT, _Traits, _Allocator>::__init(_InputIterator __first, _InputIterator __last)
2255 #ifndef _LIBCPP_NO_EXCEPTIONS
2258 #endif // _LIBCPP_NO_EXCEPTIONS
2259 for (; __first != __last; ++__first)
2260 push_back(*__first);
2261 #ifndef _LIBCPP_NO_EXCEPTIONS
2266 __alloc_traits::deallocate(__alloc(), __get_long_pointer(), __get_long_cap());
2269 #endif // _LIBCPP_NO_EXCEPTIONS
2272 template <class _CharT, class _Traits, class _Allocator>
2273 template <class _ForwardIterator>
2276 __is_forward_iterator<_ForwardIterator>::value,
2279 basic_string<_CharT, _Traits, _Allocator>::__init(_ForwardIterator __first, _ForwardIterator __last)
2281 size_type __sz = static_cast<size_type>(_VSTD::distance(__first, __last));
2282 if (__sz > max_size())
2283 this->__throw_length_error();
2285 if (__sz < __min_cap)
2287 __set_short_size(__sz);
2288 __p = __get_short_pointer();
2292 size_type __cap = __recommend(__sz);
2293 __p = __alloc_traits::allocate(__alloc(), __cap+1);
2294 __set_long_pointer(__p);
2295 __set_long_cap(__cap+1);
2296 __set_long_size(__sz);
2298 for (; __first != __last; ++__first, (void) ++__p)
2299 traits_type::assign(*__p, *__first);
2300 traits_type::assign(*__p, value_type());
2303 template <class _CharT, class _Traits, class _Allocator>
2304 template<class _InputIterator>
2305 inline _LIBCPP_INLINE_VISIBILITY
2306 basic_string<_CharT, _Traits, _Allocator>::basic_string(_InputIterator __first, _InputIterator __last)
2308 __init(__first, __last);
2309 #if _LIBCPP_DEBUG_LEVEL >= 2
2310 __get_db()->__insert_c(this);
2314 template <class _CharT, class _Traits, class _Allocator>
2315 template<class _InputIterator>
2316 inline _LIBCPP_INLINE_VISIBILITY
2317 basic_string<_CharT, _Traits, _Allocator>::basic_string(_InputIterator __first, _InputIterator __last,
2318 const allocator_type& __a)
2321 __init(__first, __last);
2322 #if _LIBCPP_DEBUG_LEVEL >= 2
2323 __get_db()->__insert_c(this);
2327 #ifndef _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
2329 template <class _CharT, class _Traits, class _Allocator>
2330 inline _LIBCPP_INLINE_VISIBILITY
2331 basic_string<_CharT, _Traits, _Allocator>::basic_string(initializer_list<value_type> __il)
2333 __init(__il.begin(), __il.end());
2334 #if _LIBCPP_DEBUG_LEVEL >= 2
2335 __get_db()->__insert_c(this);
2339 template <class _CharT, class _Traits, class _Allocator>
2340 inline _LIBCPP_INLINE_VISIBILITY
2341 basic_string<_CharT, _Traits, _Allocator>::basic_string(initializer_list<value_type> __il, const allocator_type& __a)
2344 __init(__il.begin(), __il.end());
2345 #if _LIBCPP_DEBUG_LEVEL >= 2
2346 __get_db()->__insert_c(this);
2350 #endif // _LIBCPP_HAS_NO_GENERALIZED_INITIALIZERS
2352 template <class _CharT, class _Traits, class _Allocator>
2353 basic_string<_CharT, _Traits, _Allocator>::~basic_string()
2355 #if _LIBCPP_DEBUG_LEVEL >= 2
2356 __get_db()->__erase_c(this);
2359 __alloc_traits::deallocate(__alloc(), __get_long_pointer(), __get_long_cap());
2362 template <class _CharT, class _Traits, class _Allocator>
2364 basic_string<_CharT, _Traits, _Allocator>::__grow_by_and_replace
2365 (size_type __old_cap, size_type __delta_cap, size_type __old_sz,
2366 size_type __n_copy, size_type __n_del, size_type __n_add, const value_type* __p_new_stuff)
2368 size_type __ms = max_size();
2369 if (__delta_cap > __ms - __old_cap - 1)
2370 this->__throw_length_error();
2371 pointer __old_p = __get_pointer();
2372 size_type __cap = __old_cap < __ms / 2 - __alignment ?
2373 __recommend(_VSTD::max(__old_cap + __delta_cap, 2 * __old_cap)) :
2375 pointer __p = __alloc_traits::allocate(__alloc(), __cap+1);
2376 __invalidate_all_iterators();
2378 traits_type::copy(_VSTD::__to_raw_pointer(__p),
2379 _VSTD::__to_raw_pointer(__old_p), __n_copy);
2381 traits_type::copy(_VSTD::__to_raw_pointer(__p) + __n_copy, __p_new_stuff, __n_add);
2382 size_type __sec_cp_sz = __old_sz - __n_del - __n_copy;
2383 if (__sec_cp_sz != 0)
2384 traits_type::copy(_VSTD::__to_raw_pointer(__p) + __n_copy + __n_add,
2385 _VSTD::__to_raw_pointer(__old_p) + __n_copy + __n_del, __sec_cp_sz);
2386 if (__old_cap+1 != __min_cap)
2387 __alloc_traits::deallocate(__alloc(), __old_p, __old_cap+1);
2388 __set_long_pointer(__p);
2389 __set_long_cap(__cap+1);
2390 __old_sz = __n_copy + __n_add + __sec_cp_sz;
2391 __set_long_size(__old_sz);
2392 traits_type::assign(__p[__old_sz], value_type());
2395 template <class _CharT, class _Traits, class _Allocator>
2397 basic_string<_CharT, _Traits, _Allocator>::__grow_by(size_type __old_cap, size_type __delta_cap, size_type __old_sz,
2398 size_type __n_copy, size_type __n_del, size_type __n_add)
2400 size_type __ms = max_size();
2401 if (__delta_cap > __ms - __old_cap)
2402 this->__throw_length_error();
2403 pointer __old_p = __get_pointer();
2404 size_type __cap = __old_cap < __ms / 2 - __alignment ?
2405 __recommend(_VSTD::max(__old_cap + __delta_cap, 2 * __old_cap)) :
2407 pointer __p = __alloc_traits::allocate(__alloc(), __cap+1);
2408 __invalidate_all_iterators();
2410 traits_type::copy(_VSTD::__to_raw_pointer(__p),
2411 _VSTD::__to_raw_pointer(__old_p), __n_copy);
2412 size_type __sec_cp_sz = __old_sz - __n_del - __n_copy;
2413 if (__sec_cp_sz != 0)
2414 traits_type::copy(_VSTD::__to_raw_pointer(__p) + __n_copy + __n_add,
2415 _VSTD::__to_raw_pointer(__old_p) + __n_copy + __n_del,
2417 if (__old_cap+1 != __min_cap)
2418 __alloc_traits::deallocate(__alloc(), __old_p, __old_cap+1);
2419 __set_long_pointer(__p);
2420 __set_long_cap(__cap+1);
2425 template <class _CharT, class _Traits, class _Allocator>
2426 basic_string<_CharT, _Traits, _Allocator>&
2427 basic_string<_CharT, _Traits, _Allocator>::assign(const value_type* __s, size_type __n)
2429 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::assign received nullptr");
2430 size_type __cap = capacity();
2433 value_type* __p = _VSTD::__to_raw_pointer(__get_pointer());
2434 traits_type::move(__p, __s, __n);
2435 traits_type::assign(__p[__n], value_type());
2437 __invalidate_iterators_past(__n);
2441 size_type __sz = size();
2442 __grow_by_and_replace(__cap, __n - __cap, __sz, 0, __sz, __n, __s);
2447 template <class _CharT, class _Traits, class _Allocator>
2448 basic_string<_CharT, _Traits, _Allocator>&
2449 basic_string<_CharT, _Traits, _Allocator>::assign(size_type __n, value_type __c)
2451 size_type __cap = capacity();
2454 size_type __sz = size();
2455 __grow_by(__cap, __n - __cap, __sz, 0, __sz);
2458 __invalidate_iterators_past(__n);
2459 value_type* __p = _VSTD::__to_raw_pointer(__get_pointer());
2460 traits_type::assign(__p, __n, __c);
2461 traits_type::assign(__p[__n], value_type());
2466 template <class _CharT, class _Traits, class _Allocator>
2467 basic_string<_CharT, _Traits, _Allocator>&
2468 basic_string<_CharT, _Traits, _Allocator>::operator=(value_type __c)
2473 __p = __get_long_pointer();
2478 __p = __get_short_pointer();
2479 __set_short_size(1);
2481 traits_type::assign(*__p, __c);
2482 traits_type::assign(*++__p, value_type());
2483 __invalidate_iterators_past(1);
2487 template <class _CharT, class _Traits, class _Allocator>
2488 basic_string<_CharT, _Traits, _Allocator>&
2489 basic_string<_CharT, _Traits, _Allocator>::operator=(const basic_string& __str)
2493 __copy_assign_alloc(__str);
2494 assign(__str.data(), __str.size());
2499 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
2501 template <class _CharT, class _Traits, class _Allocator>
2502 inline _LIBCPP_INLINE_VISIBILITY
2504 basic_string<_CharT, _Traits, _Allocator>::__move_assign(basic_string& __str, false_type)
2505 _NOEXCEPT_(__alloc_traits::is_always_equal::value)
2507 if (__alloc() != __str.__alloc())
2510 __move_assign(__str, true_type());
2513 template <class _CharT, class _Traits, class _Allocator>
2514 inline _LIBCPP_INLINE_VISIBILITY
2516 basic_string<_CharT, _Traits, _Allocator>::__move_assign(basic_string& __str, true_type)
2517 #if _LIBCPP_STD_VER > 14
2520 _NOEXCEPT_(is_nothrow_move_assignable<allocator_type>::value)
2525 __r_.first() = __str.__r_.first();
2526 __move_assign_alloc(__str);
2530 template <class _CharT, class _Traits, class _Allocator>
2531 inline _LIBCPP_INLINE_VISIBILITY
2532 basic_string<_CharT, _Traits, _Allocator>&
2533 basic_string<_CharT, _Traits, _Allocator>::operator=(basic_string&& __str)
2534 _NOEXCEPT_((__noexcept_move_assign_container<_Allocator, __alloc_traits>::value))
2536 __move_assign(__str, integral_constant<bool,
2537 __alloc_traits::propagate_on_container_move_assignment::value>());
2543 template <class _CharT, class _Traits, class _Allocator>
2544 template<class _InputIterator>
2547 __is_exactly_input_iterator <_InputIterator>::value
2548 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value,
2549 basic_string<_CharT, _Traits, _Allocator>&
2551 basic_string<_CharT, _Traits, _Allocator>::assign(_InputIterator __first, _InputIterator __last)
2553 basic_string __temp(__first, __last, __alloc());
2554 assign(__temp.data(), __temp.size());
2558 template <class _CharT, class _Traits, class _Allocator>
2559 template<class _ForwardIterator>
2562 __is_forward_iterator<_ForwardIterator>::value
2563 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value,
2564 basic_string<_CharT, _Traits, _Allocator>&
2566 basic_string<_CharT, _Traits, _Allocator>::assign(_ForwardIterator __first, _ForwardIterator __last)
2568 size_type __n = static_cast<size_type>(_VSTD::distance(__first, __last));
2569 size_type __cap = capacity();
2572 size_type __sz = size();
2573 __grow_by(__cap, __n - __cap, __sz, 0, __sz);
2576 __invalidate_iterators_past(__n);
2577 pointer __p = __get_pointer();
2578 for (; __first != __last; ++__first, ++__p)
2579 traits_type::assign(*__p, *__first);
2580 traits_type::assign(*__p, value_type());
2585 template <class _CharT, class _Traits, class _Allocator>
2586 basic_string<_CharT, _Traits, _Allocator>&
2587 basic_string<_CharT, _Traits, _Allocator>::assign(const basic_string& __str, size_type __pos, size_type __n)
2589 size_type __sz = __str.size();
2591 this->__throw_out_of_range();
2592 return assign(__str.data() + __pos, _VSTD::min(__n, __sz - __pos));
2595 template <class _CharT, class _Traits, class _Allocator>
2596 basic_string<_CharT, _Traits, _Allocator>&
2597 basic_string<_CharT, _Traits, _Allocator>::assign(const value_type* __s)
2599 _LIBCPP_ASSERT(__s != nullptr, "string::assign received nullptr");
2600 return assign(__s, traits_type::length(__s));
2605 template <class _CharT, class _Traits, class _Allocator>
2606 basic_string<_CharT, _Traits, _Allocator>&
2607 basic_string<_CharT, _Traits, _Allocator>::append(const value_type* __s, size_type __n)
2609 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::append received nullptr");
2610 size_type __cap = capacity();
2611 size_type __sz = size();
2612 if (__cap - __sz >= __n)
2616 value_type* __p = _VSTD::__to_raw_pointer(__get_pointer());
2617 traits_type::copy(__p + __sz, __s, __n);
2620 traits_type::assign(__p[__sz], value_type());
2624 __grow_by_and_replace(__cap, __sz + __n - __cap, __sz, __sz, 0, __n, __s);
2628 template <class _CharT, class _Traits, class _Allocator>
2629 basic_string<_CharT, _Traits, _Allocator>&
2630 basic_string<_CharT, _Traits, _Allocator>::append(size_type __n, value_type __c)
2634 size_type __cap = capacity();
2635 size_type __sz = size();
2636 if (__cap - __sz < __n)
2637 __grow_by(__cap, __sz + __n - __cap, __sz, __sz, 0);
2638 pointer __p = __get_pointer();
2639 traits_type::assign(_VSTD::__to_raw_pointer(__p) + __sz, __n, __c);
2642 traits_type::assign(__p[__sz], value_type());
2647 template <class _CharT, class _Traits, class _Allocator>
2649 basic_string<_CharT, _Traits, _Allocator>::push_back(value_type __c)
2651 bool __is_short = !__is_long();
2656 __cap = __min_cap - 1;
2657 __sz = __get_short_size();
2661 __cap = __get_long_cap() - 1;
2662 __sz = __get_long_size();
2666 __grow_by(__cap, 1, __sz, __sz, 0);
2667 __is_short = !__is_long();
2672 __p = __get_short_pointer() + __sz;
2673 __set_short_size(__sz+1);
2677 __p = __get_long_pointer() + __sz;
2678 __set_long_size(__sz+1);
2680 traits_type::assign(*__p, __c);
2681 traits_type::assign(*++__p, value_type());
2684 template <class _CharT, class _Traits, class _Allocator>
2685 template<class _InputIterator>
2688 __is_exactly_input_iterator<_InputIterator>::value
2689 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value,
2690 basic_string<_CharT, _Traits, _Allocator>&
2692 basic_string<_CharT, _Traits, _Allocator>::append(_InputIterator __first, _InputIterator __last)
2694 basic_string __temp (__first, __last, __alloc());
2695 append(__temp.data(), __temp.size());
2699 template <class _CharT, class _Traits, class _Allocator>
2700 template<class _ForwardIterator>
2703 __is_forward_iterator<_ForwardIterator>::value
2704 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value,
2705 basic_string<_CharT, _Traits, _Allocator>&
2707 basic_string<_CharT, _Traits, _Allocator>::append(_ForwardIterator __first, _ForwardIterator __last)
2709 size_type __sz = size();
2710 size_type __cap = capacity();
2711 size_type __n = static_cast<size_type>(_VSTD::distance(__first, __last));
2714 if (__cap - __sz < __n)
2715 __grow_by(__cap, __sz + __n - __cap, __sz, __sz, 0);
2716 pointer __p = __get_pointer() + __sz;
2717 for (; __first != __last; ++__p, ++__first)
2718 traits_type::assign(*__p, *__first);
2719 traits_type::assign(*__p, value_type());
2720 __set_size(__sz + __n);
2725 template <class _CharT, class _Traits, class _Allocator>
2726 inline _LIBCPP_INLINE_VISIBILITY
2727 basic_string<_CharT, _Traits, _Allocator>&
2728 basic_string<_CharT, _Traits, _Allocator>::append(const basic_string& __str)
2730 return append(__str.data(), __str.size());
2733 template <class _CharT, class _Traits, class _Allocator>
2734 basic_string<_CharT, _Traits, _Allocator>&
2735 basic_string<_CharT, _Traits, _Allocator>::append(const basic_string& __str, size_type __pos, size_type __n)
2737 size_type __sz = __str.size();
2739 this->__throw_out_of_range();
2740 return append(__str.data() + __pos, _VSTD::min(__n, __sz - __pos));
2743 template <class _CharT, class _Traits, class _Allocator>
2744 basic_string<_CharT, _Traits, _Allocator>&
2745 basic_string<_CharT, _Traits, _Allocator>::append(const value_type* __s)
2747 _LIBCPP_ASSERT(__s != nullptr, "string::append received nullptr");
2748 return append(__s, traits_type::length(__s));
2753 template <class _CharT, class _Traits, class _Allocator>
2754 basic_string<_CharT, _Traits, _Allocator>&
2755 basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos, const value_type* __s, size_type __n)
2757 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::insert received nullptr");
2758 size_type __sz = size();
2760 this->__throw_out_of_range();
2761 size_type __cap = capacity();
2762 if (__cap - __sz >= __n)
2766 value_type* __p = _VSTD::__to_raw_pointer(__get_pointer());
2767 size_type __n_move = __sz - __pos;
2770 if (__p + __pos <= __s && __s < __p + __sz)
2772 traits_type::move(__p + __pos + __n, __p + __pos, __n_move);
2774 traits_type::move(__p + __pos, __s, __n);
2777 traits_type::assign(__p[__sz], value_type());
2781 __grow_by_and_replace(__cap, __sz + __n - __cap, __sz, __pos, 0, __n, __s);
2785 template <class _CharT, class _Traits, class _Allocator>
2786 basic_string<_CharT, _Traits, _Allocator>&
2787 basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos, size_type __n, value_type __c)
2789 size_type __sz = size();
2791 this->__throw_out_of_range();
2794 size_type __cap = capacity();
2796 if (__cap - __sz >= __n)
2798 __p = _VSTD::__to_raw_pointer(__get_pointer());
2799 size_type __n_move = __sz - __pos;
2801 traits_type::move(__p + __pos + __n, __p + __pos, __n_move);
2805 __grow_by(__cap, __sz + __n - __cap, __sz, __pos, 0, __n);
2806 __p = _VSTD::__to_raw_pointer(__get_long_pointer());
2808 traits_type::assign(__p + __pos, __n, __c);
2811 traits_type::assign(__p[__sz], value_type());
2816 template <class _CharT, class _Traits, class _Allocator>
2817 template<class _InputIterator>
2820 __is_exactly_input_iterator<_InputIterator>::value
2821 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value,
2822 typename basic_string<_CharT, _Traits, _Allocator>::iterator
2824 basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, _InputIterator __first, _InputIterator __last)
2826 #if _LIBCPP_DEBUG_LEVEL >= 2
2827 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this,
2828 "string::insert(iterator, range) called with an iterator not"
2829 " referring to this string");
2831 basic_string __temp(__first, __last, __alloc());
2832 return insert(__pos, __temp.data(), __temp.data() + __temp.size());
2835 template <class _CharT, class _Traits, class _Allocator>
2836 template<class _ForwardIterator>
2839 __is_forward_iterator<_ForwardIterator>::value
2840 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value,
2841 typename basic_string<_CharT, _Traits, _Allocator>::iterator
2843 basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, _ForwardIterator __first, _ForwardIterator __last)
2845 #if _LIBCPP_DEBUG_LEVEL >= 2
2846 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this,
2847 "string::insert(iterator, range) called with an iterator not"
2848 " referring to this string");
2850 size_type __ip = static_cast<size_type>(__pos - begin());
2851 size_type __sz = size();
2852 size_type __cap = capacity();
2853 size_type __n = static_cast<size_type>(_VSTD::distance(__first, __last));
2857 if (__cap - __sz >= __n)
2859 __p = _VSTD::__to_raw_pointer(__get_pointer());
2860 size_type __n_move = __sz - __ip;
2862 traits_type::move(__p + __ip + __n, __p + __ip, __n_move);
2866 __grow_by(__cap, __sz + __n - __cap, __sz, __ip, 0, __n);
2867 __p = _VSTD::__to_raw_pointer(__get_long_pointer());
2871 traits_type::assign(__p[__sz], value_type());
2872 for (__p += __ip; __first != __last; ++__p, ++__first)
2873 traits_type::assign(*__p, *__first);
2875 return begin() + __ip;
2878 template <class _CharT, class _Traits, class _Allocator>
2879 inline _LIBCPP_INLINE_VISIBILITY
2880 basic_string<_CharT, _Traits, _Allocator>&
2881 basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos1, const basic_string& __str)
2883 return insert(__pos1, __str.data(), __str.size());
2886 template <class _CharT, class _Traits, class _Allocator>
2887 basic_string<_CharT, _Traits, _Allocator>&
2888 basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos1, const basic_string& __str,
2889 size_type __pos2, size_type __n)
2891 size_type __str_sz = __str.size();
2892 if (__pos2 > __str_sz)
2893 this->__throw_out_of_range();
2894 return insert(__pos1, __str.data() + __pos2, _VSTD::min(__n, __str_sz - __pos2));
2897 template <class _CharT, class _Traits, class _Allocator>
2898 basic_string<_CharT, _Traits, _Allocator>&
2899 basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos, const value_type* __s)
2901 _LIBCPP_ASSERT(__s != nullptr, "string::insert received nullptr");
2902 return insert(__pos, __s, traits_type::length(__s));
2905 template <class _CharT, class _Traits, class _Allocator>
2906 typename basic_string<_CharT, _Traits, _Allocator>::iterator
2907 basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, value_type __c)
2909 size_type __ip = static_cast<size_type>(__pos - begin());
2910 size_type __sz = size();
2911 size_type __cap = capacity();
2915 __grow_by(__cap, 1, __sz, __ip, 0, 1);
2916 __p = _VSTD::__to_raw_pointer(__get_long_pointer());
2920 __p = _VSTD::__to_raw_pointer(__get_pointer());
2921 size_type __n_move = __sz - __ip;
2923 traits_type::move(__p + __ip + 1, __p + __ip, __n_move);
2925 traits_type::assign(__p[__ip], __c);
2926 traits_type::assign(__p[++__sz], value_type());
2928 return begin() + static_cast<difference_type>(__ip);
2931 template <class _CharT, class _Traits, class _Allocator>
2932 inline _LIBCPP_INLINE_VISIBILITY
2933 typename basic_string<_CharT, _Traits, _Allocator>::iterator
2934 basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, size_type __n, value_type __c)
2936 #if _LIBCPP_DEBUG_LEVEL >= 2
2937 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this,
2938 "string::insert(iterator, n, value) called with an iterator not"
2939 " referring to this string");
2941 difference_type __p = __pos - begin();
2942 insert(static_cast<size_type>(__p), __n, __c);
2943 return begin() + __p;
2948 template <class _CharT, class _Traits, class _Allocator>
2949 basic_string<_CharT, _Traits, _Allocator>&
2950 basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos, size_type __n1, const value_type* __s, size_type __n2)
2952 _LIBCPP_ASSERT(__n2 == 0 || __s != nullptr, "string::replace received nullptr");
2953 size_type __sz = size();
2955 this->__throw_out_of_range();
2956 __n1 = _VSTD::min(__n1, __sz - __pos);
2957 size_type __cap = capacity();
2958 if (__cap - __sz + __n1 >= __n2)
2960 value_type* __p = _VSTD::__to_raw_pointer(__get_pointer());
2963 size_type __n_move = __sz - __pos - __n1;
2968 traits_type::move(__p + __pos, __s, __n2);
2969 traits_type::move(__p + __pos + __n2, __p + __pos + __n1, __n_move);
2972 if (__p + __pos < __s && __s < __p + __sz)
2974 if (__p + __pos + __n1 <= __s)
2976 else // __p + __pos < __s < __p + __pos + __n1
2978 traits_type::move(__p + __pos, __s, __n1);
2985 traits_type::move(__p + __pos + __n2, __p + __pos + __n1, __n_move);
2988 traits_type::move(__p + __pos, __s, __n2);
2990 __sz += __n2 - __n1;
2992 __invalidate_iterators_past(__sz);
2993 traits_type::assign(__p[__sz], value_type());
2996 __grow_by_and_replace(__cap, __sz - __n1 + __n2 - __cap, __sz, __pos, __n1, __n2, __s);
3000 template <class _CharT, class _Traits, class _Allocator>
3001 basic_string<_CharT, _Traits, _Allocator>&
3002 basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos, size_type __n1, size_type __n2, value_type __c)
3004 size_type __sz = size();
3006 this->__throw_out_of_range();
3007 __n1 = _VSTD::min(__n1, __sz - __pos);
3008 size_type __cap = capacity();
3010 if (__cap - __sz + __n1 >= __n2)
3012 __p = _VSTD::__to_raw_pointer(__get_pointer());
3015 size_type __n_move = __sz - __pos - __n1;
3017 traits_type::move(__p + __pos + __n2, __p + __pos + __n1, __n_move);
3022 __grow_by(__cap, __sz - __n1 + __n2 - __cap, __sz, __pos, __n1, __n2);
3023 __p = _VSTD::__to_raw_pointer(__get_long_pointer());
3025 traits_type::assign(__p + __pos, __n2, __c);
3026 __sz += __n2 - __n1;
3028 __invalidate_iterators_past(__sz);
3029 traits_type::assign(__p[__sz], value_type());
3033 template <class _CharT, class _Traits, class _Allocator>
3034 template<class _InputIterator>
3037 __is_input_iterator<_InputIterator>::value,
3038 basic_string<_CharT, _Traits, _Allocator>&
3040 basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2,
3041 _InputIterator __j1, _InputIterator __j2)
3043 basic_string __temp(__j1, __j2, __alloc());
3044 return this->replace(__i1, __i2, __temp);
3047 template <class _CharT, class _Traits, class _Allocator>
3048 inline _LIBCPP_INLINE_VISIBILITY
3049 basic_string<_CharT, _Traits, _Allocator>&
3050 basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos1, size_type __n1, const basic_string& __str)
3052 return replace(__pos1, __n1, __str.data(), __str.size());
3055 template <class _CharT, class _Traits, class _Allocator>
3056 basic_string<_CharT, _Traits, _Allocator>&
3057 basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos1, size_type __n1, const basic_string& __str,
3058 size_type __pos2, size_type __n2)
3060 size_type __str_sz = __str.size();
3061 if (__pos2 > __str_sz)
3062 this->__throw_out_of_range();
3063 return replace(__pos1, __n1, __str.data() + __pos2, _VSTD::min(__n2, __str_sz - __pos2));
3066 template <class _CharT, class _Traits, class _Allocator>
3067 basic_string<_CharT, _Traits, _Allocator>&
3068 basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos, size_type __n1, const value_type* __s)
3070 _LIBCPP_ASSERT(__s != nullptr, "string::replace received nullptr");
3071 return replace(__pos, __n1, __s, traits_type::length(__s));
3074 template <class _CharT, class _Traits, class _Allocator>
3075 inline _LIBCPP_INLINE_VISIBILITY
3076 basic_string<_CharT, _Traits, _Allocator>&
3077 basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, const basic_string& __str)
3079 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1),
3080 __str.data(), __str.size());
3083 template <class _CharT, class _Traits, class _Allocator>
3084 inline _LIBCPP_INLINE_VISIBILITY
3085 basic_string<_CharT, _Traits, _Allocator>&
3086 basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, const value_type* __s, size_type __n)
3088 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1), __s, __n);
3091 template <class _CharT, class _Traits, class _Allocator>
3092 inline _LIBCPP_INLINE_VISIBILITY
3093 basic_string<_CharT, _Traits, _Allocator>&
3094 basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, const value_type* __s)
3096 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1), __s);
3099 template <class _CharT, class _Traits, class _Allocator>
3100 inline _LIBCPP_INLINE_VISIBILITY
3101 basic_string<_CharT, _Traits, _Allocator>&
3102 basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, size_type __n, value_type __c)
3104 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1), __n, __c);
3109 template <class _CharT, class _Traits, class _Allocator>
3110 basic_string<_CharT, _Traits, _Allocator>&
3111 basic_string<_CharT, _Traits, _Allocator>::erase(size_type __pos, size_type __n)
3113 size_type __sz = size();
3115 this->__throw_out_of_range();
3118 value_type* __p = _VSTD::__to_raw_pointer(__get_pointer());
3119 __n = _VSTD::min(__n, __sz - __pos);
3120 size_type __n_move = __sz - __pos - __n;
3122 traits_type::move(__p + __pos, __p + __pos + __n, __n_move);
3125 __invalidate_iterators_past(__sz);
3126 traits_type::assign(__p[__sz], value_type());
3131 template <class _CharT, class _Traits, class _Allocator>
3132 inline _LIBCPP_INLINE_VISIBILITY
3133 typename basic_string<_CharT, _Traits, _Allocator>::iterator
3134 basic_string<_CharT, _Traits, _Allocator>::erase(const_iterator __pos)
3136 #if _LIBCPP_DEBUG_LEVEL >= 2
3137 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this,
3138 "string::erase(iterator) called with an iterator not"
3139 " referring to this string");
3141 _LIBCPP_ASSERT(__pos != end(),
3142 "string::erase(iterator) called with a non-dereferenceable iterator");
3143 iterator __b = begin();
3144 size_type __r = static_cast<size_type>(__pos - __b);
3146 return __b + static_cast<difference_type>(__r);
3149 template <class _CharT, class _Traits, class _Allocator>
3150 inline _LIBCPP_INLINE_VISIBILITY
3151 typename basic_string<_CharT, _Traits, _Allocator>::iterator
3152 basic_string<_CharT, _Traits, _Allocator>::erase(const_iterator __first, const_iterator __last)
3154 #if _LIBCPP_DEBUG_LEVEL >= 2
3155 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__first) == this,
3156 "string::erase(iterator, iterator) called with an iterator not"
3157 " referring to this string");
3159 _LIBCPP_ASSERT(__first <= __last, "string::erase(first, last) called with invalid range");
3160 iterator __b = begin();
3161 size_type __r = static_cast<size_type>(__first - __b);
3162 erase(__r, static_cast<size_type>(__last - __first));
3163 return __b + static_cast<difference_type>(__r);
3166 template <class _CharT, class _Traits, class _Allocator>
3167 inline _LIBCPP_INLINE_VISIBILITY
3169 basic_string<_CharT, _Traits, _Allocator>::pop_back()
3171 _LIBCPP_ASSERT(!empty(), "string::pop_back(): string is already empty");
3175 __sz = __get_long_size() - 1;
3176 __set_long_size(__sz);
3177 traits_type::assign(*(__get_long_pointer() + __sz), value_type());
3181 __sz = __get_short_size() - 1;
3182 __set_short_size(__sz);
3183 traits_type::assign(*(__get_short_pointer() + __sz), value_type());
3185 __invalidate_iterators_past(__sz);
3188 template <class _CharT, class _Traits, class _Allocator>
3189 inline _LIBCPP_INLINE_VISIBILITY
3191 basic_string<_CharT, _Traits, _Allocator>::clear() _NOEXCEPT
3193 __invalidate_all_iterators();
3196 traits_type::assign(*__get_long_pointer(), value_type());
3201 traits_type::assign(*__get_short_pointer(), value_type());
3202 __set_short_size(0);
3206 template <class _CharT, class _Traits, class _Allocator>
3207 inline _LIBCPP_INLINE_VISIBILITY
3209 basic_string<_CharT, _Traits, _Allocator>::__erase_to_end(size_type __pos)
3213 traits_type::assign(*(__get_long_pointer() + __pos), value_type());
3214 __set_long_size(__pos);
3218 traits_type::assign(*(__get_short_pointer() + __pos), value_type());
3219 __set_short_size(__pos);
3221 __invalidate_iterators_past(__pos);
3224 template <class _CharT, class _Traits, class _Allocator>
3226 basic_string<_CharT, _Traits, _Allocator>::resize(size_type __n, value_type __c)
3228 size_type __sz = size();
3230 append(__n - __sz, __c);
3232 __erase_to_end(__n);
3235 template <class _CharT, class _Traits, class _Allocator>
3236 inline _LIBCPP_INLINE_VISIBILITY
3237 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3238 basic_string<_CharT, _Traits, _Allocator>::max_size() const _NOEXCEPT
3240 size_type __m = __alloc_traits::max_size(__alloc());
3241 #if _LIBCPP_BIG_ENDIAN
3242 return (__m <= ~__long_mask ? __m : __m/2) - __alignment;
3244 return __m - __alignment;
3248 template <class _CharT, class _Traits, class _Allocator>
3250 basic_string<_CharT, _Traits, _Allocator>::reserve(size_type __res_arg)
3252 if (__res_arg > max_size())
3253 this->__throw_length_error();
3254 size_type __cap = capacity();
3255 size_type __sz = size();
3256 __res_arg = _VSTD::max(__res_arg, __sz);
3257 __res_arg = __recommend(__res_arg);
3258 if (__res_arg != __cap)
3260 pointer __new_data, __p;
3261 bool __was_long, __now_long;
3262 if (__res_arg == __min_cap - 1)
3266 __new_data = __get_short_pointer();
3267 __p = __get_long_pointer();
3271 if (__res_arg > __cap)
3272 __new_data = __alloc_traits::allocate(__alloc(), __res_arg+1);
3275 #ifndef _LIBCPP_NO_EXCEPTIONS
3278 #endif // _LIBCPP_NO_EXCEPTIONS
3279 __new_data = __alloc_traits::allocate(__alloc(), __res_arg+1);
3280 #ifndef _LIBCPP_NO_EXCEPTIONS
3286 #else // _LIBCPP_NO_EXCEPTIONS
3287 if (__new_data == nullptr)
3289 #endif // _LIBCPP_NO_EXCEPTIONS
3292 __was_long = __is_long();
3293 __p = __get_pointer();
3295 traits_type::copy(_VSTD::__to_raw_pointer(__new_data),
3296 _VSTD::__to_raw_pointer(__p), size()+1);
3298 __alloc_traits::deallocate(__alloc(), __p, __cap+1);
3301 __set_long_cap(__res_arg+1);
3302 __set_long_size(__sz);
3303 __set_long_pointer(__new_data);
3306 __set_short_size(__sz);
3307 __invalidate_all_iterators();
3311 template <class _CharT, class _Traits, class _Allocator>
3312 inline _LIBCPP_INLINE_VISIBILITY
3313 typename basic_string<_CharT, _Traits, _Allocator>::const_reference
3314 basic_string<_CharT, _Traits, _Allocator>::operator[](size_type __pos) const
3316 _LIBCPP_ASSERT(__pos <= size(), "string index out of bounds");
3317 return *(data() + __pos);
3320 template <class _CharT, class _Traits, class _Allocator>
3321 inline _LIBCPP_INLINE_VISIBILITY
3322 typename basic_string<_CharT, _Traits, _Allocator>::reference
3323 basic_string<_CharT, _Traits, _Allocator>::operator[](size_type __pos)
3325 _LIBCPP_ASSERT(__pos <= size(), "string index out of bounds");
3326 return *(__get_pointer() + __pos);
3329 template <class _CharT, class _Traits, class _Allocator>
3330 typename basic_string<_CharT, _Traits, _Allocator>::const_reference
3331 basic_string<_CharT, _Traits, _Allocator>::at(size_type __n) const
3334 this->__throw_out_of_range();
3335 return (*this)[__n];
3338 template <class _CharT, class _Traits, class _Allocator>
3339 typename basic_string<_CharT, _Traits, _Allocator>::reference
3340 basic_string<_CharT, _Traits, _Allocator>::at(size_type __n)
3343 this->__throw_out_of_range();
3344 return (*this)[__n];
3347 template <class _CharT, class _Traits, class _Allocator>
3348 inline _LIBCPP_INLINE_VISIBILITY
3349 typename basic_string<_CharT, _Traits, _Allocator>::reference
3350 basic_string<_CharT, _Traits, _Allocator>::front()
3352 _LIBCPP_ASSERT(!empty(), "string::front(): string is empty");
3353 return *__get_pointer();
3356 template <class _CharT, class _Traits, class _Allocator>
3357 inline _LIBCPP_INLINE_VISIBILITY
3358 typename basic_string<_CharT, _Traits, _Allocator>::const_reference
3359 basic_string<_CharT, _Traits, _Allocator>::front() const
3361 _LIBCPP_ASSERT(!empty(), "string::front(): string is empty");
3365 template <class _CharT, class _Traits, class _Allocator>
3366 inline _LIBCPP_INLINE_VISIBILITY
3367 typename basic_string<_CharT, _Traits, _Allocator>::reference
3368 basic_string<_CharT, _Traits, _Allocator>::back()
3370 _LIBCPP_ASSERT(!empty(), "string::back(): string is empty");
3371 return *(__get_pointer() + size() - 1);
3374 template <class _CharT, class _Traits, class _Allocator>
3375 inline _LIBCPP_INLINE_VISIBILITY
3376 typename basic_string<_CharT, _Traits, _Allocator>::const_reference
3377 basic_string<_CharT, _Traits, _Allocator>::back() const
3379 _LIBCPP_ASSERT(!empty(), "string::back(): string is empty");
3380 return *(data() + size() - 1);
3383 template <class _CharT, class _Traits, class _Allocator>
3384 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3385 basic_string<_CharT, _Traits, _Allocator>::copy(value_type* __s, size_type __n, size_type __pos) const
3387 size_type __sz = size();
3389 this->__throw_out_of_range();
3390 size_type __rlen = _VSTD::min(__n, __sz - __pos);
3391 traits_type::copy(__s, data() + __pos, __rlen);
3395 template <class _CharT, class _Traits, class _Allocator>
3396 inline _LIBCPP_INLINE_VISIBILITY
3397 basic_string<_CharT, _Traits, _Allocator>
3398 basic_string<_CharT, _Traits, _Allocator>::substr(size_type __pos, size_type __n) const
3400 return basic_string(*this, __pos, __n, __alloc());
3403 template <class _CharT, class _Traits, class _Allocator>
3404 inline _LIBCPP_INLINE_VISIBILITY
3406 basic_string<_CharT, _Traits, _Allocator>::swap(basic_string& __str)
3407 #if _LIBCPP_STD_VER >= 14
3410 _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value ||
3411 __is_nothrow_swappable<allocator_type>::value)
3414 #if _LIBCPP_DEBUG_LEVEL >= 2
3416 __get_db()->__invalidate_all(this);
3417 if (!__str.__is_long())
3418 __get_db()->__invalidate_all(&__str);
3419 __get_db()->swap(this, &__str);
3421 _VSTD::swap(__r_.first(), __str.__r_.first());
3422 __swap_allocator(__alloc(), __str.__alloc());
3427 template <class _Traits>
3428 struct _LIBCPP_HIDDEN __traits_eq
3430 typedef typename _Traits::char_type char_type;
3431 _LIBCPP_INLINE_VISIBILITY
3432 bool operator()(const char_type& __x, const char_type& __y) _NOEXCEPT
3433 {return _Traits::eq(__x, __y);}
3436 template<class _CharT, class _Traits, class _Allocator>
3437 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3438 basic_string<_CharT, _Traits, _Allocator>::find(const value_type* __s,
3440 size_type __n) const _NOEXCEPT
3442 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find(): received nullptr");
3443 return _VSTD::__str_find<value_type, size_type, traits_type, npos>
3444 (data(), size(), __s, __pos, __n);
3447 template<class _CharT, class _Traits, class _Allocator>
3448 inline _LIBCPP_INLINE_VISIBILITY
3449 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3450 basic_string<_CharT, _Traits, _Allocator>::find(const basic_string& __str,
3451 size_type __pos) const _NOEXCEPT
3453 return _VSTD::__str_find<value_type, size_type, traits_type, npos>
3454 (data(), size(), __str.data(), __pos, __str.size());
3457 template<class _CharT, class _Traits, class _Allocator>
3458 inline _LIBCPP_INLINE_VISIBILITY
3459 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3460 basic_string<_CharT, _Traits, _Allocator>::find(const value_type* __s,
3461 size_type __pos) const _NOEXCEPT
3463 _LIBCPP_ASSERT(__s != nullptr, "string::find(): received nullptr");
3464 return _VSTD::__str_find<value_type, size_type, traits_type, npos>
3465 (data(), size(), __s, __pos, traits_type::length(__s));
3468 template<class _CharT, class _Traits, class _Allocator>
3469 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3470 basic_string<_CharT, _Traits, _Allocator>::find(value_type __c,
3471 size_type __pos) const _NOEXCEPT
3473 return _VSTD::__str_find<value_type, size_type, traits_type, npos>
3474 (data(), size(), __c, __pos);
3479 template<class _CharT, class _Traits, class _Allocator>
3480 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3481 basic_string<_CharT, _Traits, _Allocator>::rfind(const value_type* __s,
3483 size_type __n) const _NOEXCEPT
3485 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::rfind(): received nullptr");
3486 return _VSTD::__str_rfind<value_type, size_type, traits_type, npos>
3487 (data(), size(), __s, __pos, __n);
3490 template<class _CharT, class _Traits, class _Allocator>
3491 inline _LIBCPP_INLINE_VISIBILITY
3492 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3493 basic_string<_CharT, _Traits, _Allocator>::rfind(const basic_string& __str,
3494 size_type __pos) const _NOEXCEPT
3496 return _VSTD::__str_rfind<value_type, size_type, traits_type, npos>
3497 (data(), size(), __str.data(), __pos, __str.size());
3500 template<class _CharT, class _Traits, class _Allocator>
3501 inline _LIBCPP_INLINE_VISIBILITY
3502 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3503 basic_string<_CharT, _Traits, _Allocator>::rfind(const value_type* __s,
3504 size_type __pos) const _NOEXCEPT
3506 _LIBCPP_ASSERT(__s != nullptr, "string::rfind(): received nullptr");
3507 return _VSTD::__str_rfind<value_type, size_type, traits_type, npos>
3508 (data(), size(), __s, __pos, traits_type::length(__s));
3511 template<class _CharT, class _Traits, class _Allocator>
3512 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3513 basic_string<_CharT, _Traits, _Allocator>::rfind(value_type __c,
3514 size_type __pos) const _NOEXCEPT
3516 return _VSTD::__str_rfind<value_type, size_type, traits_type, npos>
3517 (data(), size(), __c, __pos);
3522 template<class _CharT, class _Traits, class _Allocator>
3523 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3524 basic_string<_CharT, _Traits, _Allocator>::find_first_of(const value_type* __s,
3526 size_type __n) const _NOEXCEPT
3528 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_first_of(): received nullptr");
3529 return _VSTD::__str_find_first_of<value_type, size_type, traits_type, npos>
3530 (data(), size(), __s, __pos, __n);
3533 template<class _CharT, class _Traits, class _Allocator>
3534 inline _LIBCPP_INLINE_VISIBILITY
3535 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3536 basic_string<_CharT, _Traits, _Allocator>::find_first_of(const basic_string& __str,
3537 size_type __pos) const _NOEXCEPT
3539 return _VSTD::__str_find_first_of<value_type, size_type, traits_type, npos>
3540 (data(), size(), __str.data(), __pos, __str.size());
3543 template<class _CharT, class _Traits, class _Allocator>
3544 inline _LIBCPP_INLINE_VISIBILITY
3545 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3546 basic_string<_CharT, _Traits, _Allocator>::find_first_of(const value_type* __s,
3547 size_type __pos) const _NOEXCEPT
3549 _LIBCPP_ASSERT(__s != nullptr, "string::find_first_of(): received nullptr");
3550 return _VSTD::__str_find_first_of<value_type, size_type, traits_type, npos>
3551 (data(), size(), __s, __pos, traits_type::length(__s));
3554 template<class _CharT, class _Traits, class _Allocator>
3555 inline _LIBCPP_INLINE_VISIBILITY
3556 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3557 basic_string<_CharT, _Traits, _Allocator>::find_first_of(value_type __c,
3558 size_type __pos) const _NOEXCEPT
3560 return find(__c, __pos);
3565 template<class _CharT, class _Traits, class _Allocator>
3566 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3567 basic_string<_CharT, _Traits, _Allocator>::find_last_of(const value_type* __s,
3569 size_type __n) const _NOEXCEPT
3571 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_last_of(): received nullptr");
3572 return _VSTD::__str_find_last_of<value_type, size_type, traits_type, npos>
3573 (data(), size(), __s, __pos, __n);
3576 template<class _CharT, class _Traits, class _Allocator>
3577 inline _LIBCPP_INLINE_VISIBILITY
3578 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3579 basic_string<_CharT, _Traits, _Allocator>::find_last_of(const basic_string& __str,
3580 size_type __pos) const _NOEXCEPT
3582 return _VSTD::__str_find_last_of<value_type, size_type, traits_type, npos>
3583 (data(), size(), __str.data(), __pos, __str.size());
3586 template<class _CharT, class _Traits, class _Allocator>
3587 inline _LIBCPP_INLINE_VISIBILITY
3588 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3589 basic_string<_CharT, _Traits, _Allocator>::find_last_of(const value_type* __s,
3590 size_type __pos) const _NOEXCEPT
3592 _LIBCPP_ASSERT(__s != nullptr, "string::find_last_of(): received nullptr");
3593 return _VSTD::__str_find_last_of<value_type, size_type, traits_type, npos>
3594 (data(), size(), __s, __pos, traits_type::length(__s));
3597 template<class _CharT, class _Traits, class _Allocator>
3598 inline _LIBCPP_INLINE_VISIBILITY
3599 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3600 basic_string<_CharT, _Traits, _Allocator>::find_last_of(value_type __c,
3601 size_type __pos) const _NOEXCEPT
3603 return rfind(__c, __pos);
3606 // find_first_not_of
3608 template<class _CharT, class _Traits, class _Allocator>
3609 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3610 basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(const value_type* __s,
3612 size_type __n) const _NOEXCEPT
3614 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_first_not_of(): received nullptr");
3615 return _VSTD::__str_find_first_not_of<value_type, size_type, traits_type, npos>
3616 (data(), size(), __s, __pos, __n);
3619 template<class _CharT, class _Traits, class _Allocator>
3620 inline _LIBCPP_INLINE_VISIBILITY
3621 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3622 basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(const basic_string& __str,
3623 size_type __pos) const _NOEXCEPT
3625 return _VSTD::__str_find_first_not_of<value_type, size_type, traits_type, npos>
3626 (data(), size(), __str.data(), __pos, __str.size());
3629 template<class _CharT, class _Traits, class _Allocator>
3630 inline _LIBCPP_INLINE_VISIBILITY
3631 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3632 basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(const value_type* __s,
3633 size_type __pos) const _NOEXCEPT
3635 _LIBCPP_ASSERT(__s != nullptr, "string::find_first_not_of(): received nullptr");
3636 return _VSTD::__str_find_first_not_of<value_type, size_type, traits_type, npos>
3637 (data(), size(), __s, __pos, traits_type::length(__s));
3640 template<class _CharT, class _Traits, class _Allocator>
3641 inline _LIBCPP_INLINE_VISIBILITY
3642 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3643 basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(value_type __c,
3644 size_type __pos) const _NOEXCEPT
3646 return _VSTD::__str_find_first_not_of<value_type, size_type, traits_type, npos>
3647 (data(), size(), __c, __pos);
3652 template<class _CharT, class _Traits, class _Allocator>
3653 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3654 basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(const value_type* __s,
3656 size_type __n) const _NOEXCEPT
3658 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_last_not_of(): received nullptr");
3659 return _VSTD::__str_find_last_not_of<value_type, size_type, traits_type, npos>
3660 (data(), size(), __s, __pos, __n);
3663 template<class _CharT, class _Traits, class _Allocator>
3664 inline _LIBCPP_INLINE_VISIBILITY
3665 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3666 basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(const basic_string& __str,
3667 size_type __pos) const _NOEXCEPT
3669 return _VSTD::__str_find_last_not_of<value_type, size_type, traits_type, npos>
3670 (data(), size(), __str.data(), __pos, __str.size());
3673 template<class _CharT, class _Traits, class _Allocator>
3674 inline _LIBCPP_INLINE_VISIBILITY
3675 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3676 basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(const value_type* __s,
3677 size_type __pos) const _NOEXCEPT
3679 _LIBCPP_ASSERT(__s != nullptr, "string::find_last_not_of(): received nullptr");
3680 return _VSTD::__str_find_last_not_of<value_type, size_type, traits_type, npos>
3681 (data(), size(), __s, __pos, traits_type::length(__s));
3684 template<class _CharT, class _Traits, class _Allocator>
3685 inline _LIBCPP_INLINE_VISIBILITY
3686 typename basic_string<_CharT, _Traits, _Allocator>::size_type
3687 basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(value_type __c,
3688 size_type __pos) const _NOEXCEPT
3690 return _VSTD::__str_find_last_not_of<value_type, size_type, traits_type, npos>
3691 (data(), size(), __c, __pos);
3696 template <class _CharT, class _Traits, class _Allocator>
3697 inline _LIBCPP_INLINE_VISIBILITY
3699 basic_string<_CharT, _Traits, _Allocator>::compare(const basic_string& __str) const _NOEXCEPT
3701 size_t __lhs_sz = size();
3702 size_t __rhs_sz = __str.size();
3703 int __result = traits_type::compare(data(), __str.data(),
3704 _VSTD::min(__lhs_sz, __rhs_sz));
3707 if (__lhs_sz < __rhs_sz)
3709 if (__lhs_sz > __rhs_sz)
3714 template <class _CharT, class _Traits, class _Allocator>
3715 inline _LIBCPP_INLINE_VISIBILITY
3717 basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1,
3719 const basic_string& __str) const
3721 return compare(__pos1, __n1, __str.data(), __str.size());
3724 template <class _CharT, class _Traits, class _Allocator>
3726 basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1,
3728 const basic_string& __str,
3730 size_type __n2) const
3732 size_type __sz = __str.size();
3734 this->__throw_out_of_range();
3735 return compare(__pos1, __n1, __str.data() + __pos2, _VSTD::min(__n2,
3739 template <class _CharT, class _Traits, class _Allocator>
3741 basic_string<_CharT, _Traits, _Allocator>::compare(const value_type* __s) const _NOEXCEPT
3743 _LIBCPP_ASSERT(__s != nullptr, "string::compare(): received nullptr");
3744 return compare(0, npos, __s, traits_type::length(__s));
3747 template <class _CharT, class _Traits, class _Allocator>
3749 basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1,
3751 const value_type* __s) const
3753 _LIBCPP_ASSERT(__s != nullptr, "string::compare(): received nullptr");
3754 return compare(__pos1, __n1, __s, traits_type::length(__s));
3757 template <class _CharT, class _Traits, class _Allocator>
3759 basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1,
3761 const value_type* __s,
3762 size_type __n2) const
3764 _LIBCPP_ASSERT(__n2 == 0 || __s != nullptr, "string::compare(): received nullptr");
3765 size_type __sz = size();
3766 if (__pos1 > __sz || __n2 == npos)
3767 this->__throw_out_of_range();
3768 size_type __rlen = _VSTD::min(__n1, __sz - __pos1);
3769 int __r = traits_type::compare(data() + __pos1, __s, _VSTD::min(__rlen, __n2));
3774 else if (__rlen > __n2)
3782 template<class _CharT, class _Traits, class _Allocator>
3783 inline _LIBCPP_INLINE_VISIBILITY
3785 basic_string<_CharT, _Traits, _Allocator>::__invariants() const
3787 if (size() > capacity())
3789 if (capacity() < __min_cap - 1)
3793 if (data()[size()] != value_type(0))
3800 template<class _CharT, class _Traits, class _Allocator>
3801 inline _LIBCPP_INLINE_VISIBILITY
3803 operator==(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3804 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3806 size_t __lhs_sz = __lhs.size();
3807 return __lhs_sz == __rhs.size() && _Traits::compare(__lhs.data(),
3812 template<class _Allocator>
3813 inline _LIBCPP_INLINE_VISIBILITY
3815 operator==(const basic_string<char, char_traits<char>, _Allocator>& __lhs,
3816 const basic_string<char, char_traits<char>, _Allocator>& __rhs) _NOEXCEPT
3818 size_t __lhs_sz = __lhs.size();
3819 if (__lhs_sz != __rhs.size())
3821 const char* __lp = __lhs.data();
3822 const char* __rp = __rhs.data();
3823 if (__lhs.__is_long())
3824 return char_traits<char>::compare(__lp, __rp, __lhs_sz) == 0;
3825 for (; __lhs_sz != 0; --__lhs_sz, ++__lp, ++__rp)
3831 template<class _CharT, class _Traits, class _Allocator>
3832 inline _LIBCPP_INLINE_VISIBILITY
3834 operator==(const _CharT* __lhs,
3835 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3837 typedef basic_string<_CharT, _Traits, _Allocator> _String;
3838 _LIBCPP_ASSERT(__lhs != nullptr, "operator==(char*, basic_string): received nullptr");
3839 size_t __lhs_len = _Traits::length(__lhs);
3840 if (__lhs_len != __rhs.size()) return false;
3841 return __rhs.compare(0, _String::npos, __lhs, __lhs_len) == 0;
3844 template<class _CharT, class _Traits, class _Allocator>
3845 inline _LIBCPP_INLINE_VISIBILITY
3847 operator==(const basic_string<_CharT,_Traits,_Allocator>& __lhs,
3848 const _CharT* __rhs) _NOEXCEPT
3850 typedef basic_string<_CharT, _Traits, _Allocator> _String;
3851 _LIBCPP_ASSERT(__rhs != nullptr, "operator==(basic_string, char*): received nullptr");
3852 size_t __rhs_len = _Traits::length(__rhs);
3853 if (__rhs_len != __lhs.size()) return false;
3854 return __lhs.compare(0, _String::npos, __rhs, __rhs_len) == 0;
3859 template<class _CharT, class _Traits, class _Allocator>
3860 inline _LIBCPP_INLINE_VISIBILITY
3862 operator!=(const basic_string<_CharT,_Traits,_Allocator>& __lhs,
3863 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3865 return !(__lhs == __rhs);
3868 template<class _CharT, class _Traits, class _Allocator>
3869 inline _LIBCPP_INLINE_VISIBILITY
3871 operator!=(const _CharT* __lhs,
3872 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3874 return !(__lhs == __rhs);
3877 template<class _CharT, class _Traits, class _Allocator>
3878 inline _LIBCPP_INLINE_VISIBILITY
3880 operator!=(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3881 const _CharT* __rhs) _NOEXCEPT
3883 return !(__lhs == __rhs);
3888 template<class _CharT, class _Traits, class _Allocator>
3889 inline _LIBCPP_INLINE_VISIBILITY
3891 operator< (const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3892 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3894 return __lhs.compare(__rhs) < 0;
3897 template<class _CharT, class _Traits, class _Allocator>
3898 inline _LIBCPP_INLINE_VISIBILITY
3900 operator< (const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3901 const _CharT* __rhs) _NOEXCEPT
3903 return __lhs.compare(__rhs) < 0;
3906 template<class _CharT, class _Traits, class _Allocator>
3907 inline _LIBCPP_INLINE_VISIBILITY
3909 operator< (const _CharT* __lhs,
3910 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3912 return __rhs.compare(__lhs) > 0;
3917 template<class _CharT, class _Traits, class _Allocator>
3918 inline _LIBCPP_INLINE_VISIBILITY
3920 operator> (const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3921 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3923 return __rhs < __lhs;
3926 template<class _CharT, class _Traits, class _Allocator>
3927 inline _LIBCPP_INLINE_VISIBILITY
3929 operator> (const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3930 const _CharT* __rhs) _NOEXCEPT
3932 return __rhs < __lhs;
3935 template<class _CharT, class _Traits, class _Allocator>
3936 inline _LIBCPP_INLINE_VISIBILITY
3938 operator> (const _CharT* __lhs,
3939 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3941 return __rhs < __lhs;
3946 template<class _CharT, class _Traits, class _Allocator>
3947 inline _LIBCPP_INLINE_VISIBILITY
3949 operator<=(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3950 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3952 return !(__rhs < __lhs);
3955 template<class _CharT, class _Traits, class _Allocator>
3956 inline _LIBCPP_INLINE_VISIBILITY
3958 operator<=(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3959 const _CharT* __rhs) _NOEXCEPT
3961 return !(__rhs < __lhs);
3964 template<class _CharT, class _Traits, class _Allocator>
3965 inline _LIBCPP_INLINE_VISIBILITY
3967 operator<=(const _CharT* __lhs,
3968 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3970 return !(__rhs < __lhs);
3975 template<class _CharT, class _Traits, class _Allocator>
3976 inline _LIBCPP_INLINE_VISIBILITY
3978 operator>=(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3979 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3981 return !(__lhs < __rhs);
3984 template<class _CharT, class _Traits, class _Allocator>
3985 inline _LIBCPP_INLINE_VISIBILITY
3987 operator>=(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
3988 const _CharT* __rhs) _NOEXCEPT
3990 return !(__lhs < __rhs);
3993 template<class _CharT, class _Traits, class _Allocator>
3994 inline _LIBCPP_INLINE_VISIBILITY
3996 operator>=(const _CharT* __lhs,
3997 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT
3999 return !(__lhs < __rhs);
4004 template<class _CharT, class _Traits, class _Allocator>
4005 basic_string<_CharT, _Traits, _Allocator>
4006 operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
4007 const basic_string<_CharT, _Traits, _Allocator>& __rhs)
4009 basic_string<_CharT, _Traits, _Allocator> __r(__lhs.get_allocator());
4010 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = __lhs.size();
4011 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = __rhs.size();
4012 __r.__init(__lhs.data(), __lhs_sz, __lhs_sz + __rhs_sz);
4013 __r.append(__rhs.data(), __rhs_sz);
4017 template<class _CharT, class _Traits, class _Allocator>
4018 basic_string<_CharT, _Traits, _Allocator>
4019 operator+(const _CharT* __lhs , const basic_string<_CharT,_Traits,_Allocator>& __rhs)
4021 basic_string<_CharT, _Traits, _Allocator> __r(__rhs.get_allocator());
4022 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = _Traits::length(__lhs);
4023 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = __rhs.size();
4024 __r.__init(__lhs, __lhs_sz, __lhs_sz + __rhs_sz);
4025 __r.append(__rhs.data(), __rhs_sz);
4029 template<class _CharT, class _Traits, class _Allocator>
4030 basic_string<_CharT, _Traits, _Allocator>
4031 operator+(_CharT __lhs, const basic_string<_CharT,_Traits,_Allocator>& __rhs)
4033 basic_string<_CharT, _Traits, _Allocator> __r(__rhs.get_allocator());
4034 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = __rhs.size();
4035 __r.__init(&__lhs, 1, 1 + __rhs_sz);
4036 __r.append(__rhs.data(), __rhs_sz);
4040 template<class _CharT, class _Traits, class _Allocator>
4041 basic_string<_CharT, _Traits, _Allocator>
4042 operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs, const _CharT* __rhs)
4044 basic_string<_CharT, _Traits, _Allocator> __r(__lhs.get_allocator());
4045 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = __lhs.size();
4046 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = _Traits::length(__rhs);
4047 __r.__init(__lhs.data(), __lhs_sz, __lhs_sz + __rhs_sz);
4048 __r.append(__rhs, __rhs_sz);
4052 template<class _CharT, class _Traits, class _Allocator>
4053 basic_string<_CharT, _Traits, _Allocator>
4054 operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs, _CharT __rhs)
4056 basic_string<_CharT, _Traits, _Allocator> __r(__lhs.get_allocator());
4057 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = __lhs.size();
4058 __r.__init(__lhs.data(), __lhs_sz, __lhs_sz + 1);
4059 __r.push_back(__rhs);
4063 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
4065 template<class _CharT, class _Traits, class _Allocator>
4066 inline _LIBCPP_INLINE_VISIBILITY
4067 basic_string<_CharT, _Traits, _Allocator>
4068 operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, const basic_string<_CharT, _Traits, _Allocator>& __rhs)
4070 return _VSTD::move(__lhs.append(__rhs));
4073 template<class _CharT, class _Traits, class _Allocator>
4074 inline _LIBCPP_INLINE_VISIBILITY
4075 basic_string<_CharT, _Traits, _Allocator>
4076 operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs, basic_string<_CharT, _Traits, _Allocator>&& __rhs)
4078 return _VSTD::move(__rhs.insert(0, __lhs));
4081 template<class _CharT, class _Traits, class _Allocator>
4082 inline _LIBCPP_INLINE_VISIBILITY
4083 basic_string<_CharT, _Traits, _Allocator>
4084 operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, basic_string<_CharT, _Traits, _Allocator>&& __rhs)
4086 return _VSTD::move(__lhs.append(__rhs));
4089 template<class _CharT, class _Traits, class _Allocator>
4090 inline _LIBCPP_INLINE_VISIBILITY
4091 basic_string<_CharT, _Traits, _Allocator>
4092 operator+(const _CharT* __lhs , basic_string<_CharT,_Traits,_Allocator>&& __rhs)
4094 return _VSTD::move(__rhs.insert(0, __lhs));
4097 template<class _CharT, class _Traits, class _Allocator>
4098 inline _LIBCPP_INLINE_VISIBILITY
4099 basic_string<_CharT, _Traits, _Allocator>
4100 operator+(_CharT __lhs, basic_string<_CharT,_Traits,_Allocator>&& __rhs)
4102 __rhs.insert(__rhs.begin(), __lhs);
4103 return _VSTD::move(__rhs);
4106 template<class _CharT, class _Traits, class _Allocator>
4107 inline _LIBCPP_INLINE_VISIBILITY
4108 basic_string<_CharT, _Traits, _Allocator>
4109 operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, const _CharT* __rhs)
4111 return _VSTD::move(__lhs.append(__rhs));
4114 template<class _CharT, class _Traits, class _Allocator>
4115 inline _LIBCPP_INLINE_VISIBILITY
4116 basic_string<_CharT, _Traits, _Allocator>
4117 operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, _CharT __rhs)
4119 __lhs.push_back(__rhs);
4120 return _VSTD::move(__lhs);
4123 #endif // _LIBCPP_HAS_NO_RVALUE_REFERENCES
4127 template<class _CharT, class _Traits, class _Allocator>
4128 inline _LIBCPP_INLINE_VISIBILITY
4130 swap(basic_string<_CharT, _Traits, _Allocator>& __lhs,
4131 basic_string<_CharT, _Traits, _Allocator>& __rhs)
4132 _NOEXCEPT_(_NOEXCEPT_(__lhs.swap(__rhs)))
4137 #ifndef _LIBCPP_HAS_NO_UNICODE_CHARS
4139 typedef basic_string<char16_t> u16string;
4140 typedef basic_string<char32_t> u32string;
4142 #endif // _LIBCPP_HAS_NO_UNICODE_CHARS
4144 _LIBCPP_FUNC_VIS int stoi (const string& __str, size_t* __idx = 0, int __base = 10);
4145 _LIBCPP_FUNC_VIS long stol (const string& __str, size_t* __idx = 0, int __base = 10);
4146 _LIBCPP_FUNC_VIS unsigned long stoul (const string& __str, size_t* __idx = 0, int __base = 10);
4147 _LIBCPP_FUNC_VIS long long stoll (const string& __str, size_t* __idx = 0, int __base = 10);
4148 _LIBCPP_FUNC_VIS unsigned long long stoull(const string& __str, size_t* __idx = 0, int __base = 10);
4150 _LIBCPP_FUNC_VIS float stof (const string& __str, size_t* __idx = 0);
4151 _LIBCPP_FUNC_VIS double stod (const string& __str, size_t* __idx = 0);
4152 _LIBCPP_FUNC_VIS long double stold(const string& __str, size_t* __idx = 0);
4154 _LIBCPP_FUNC_VIS string to_string(int __val);
4155 _LIBCPP_FUNC_VIS string to_string(unsigned __val);
4156 _LIBCPP_FUNC_VIS string to_string(long __val);
4157 _LIBCPP_FUNC_VIS string to_string(unsigned long __val);
4158 _LIBCPP_FUNC_VIS string to_string(long long __val);
4159 _LIBCPP_FUNC_VIS string to_string(unsigned long long __val);
4160 _LIBCPP_FUNC_VIS string to_string(float __val);
4161 _LIBCPP_FUNC_VIS string to_string(double __val);
4162 _LIBCPP_FUNC_VIS string to_string(long double __val);
4164 _LIBCPP_FUNC_VIS int stoi (const wstring& __str, size_t* __idx = 0, int __base = 10);
4165 _LIBCPP_FUNC_VIS long stol (const wstring& __str, size_t* __idx = 0, int __base = 10);
4166 _LIBCPP_FUNC_VIS unsigned long stoul (const wstring& __str, size_t* __idx = 0, int __base = 10);
4167 _LIBCPP_FUNC_VIS long long stoll (const wstring& __str, size_t* __idx = 0, int __base = 10);
4168 _LIBCPP_FUNC_VIS unsigned long long stoull(const wstring& __str, size_t* __idx = 0, int __base = 10);
4170 _LIBCPP_FUNC_VIS float stof (const wstring& __str, size_t* __idx = 0);
4171 _LIBCPP_FUNC_VIS double stod (const wstring& __str, size_t* __idx = 0);
4172 _LIBCPP_FUNC_VIS long double stold(const wstring& __str, size_t* __idx = 0);
4174 _LIBCPP_FUNC_VIS wstring to_wstring(int __val);
4175 _LIBCPP_FUNC_VIS wstring to_wstring(unsigned __val);
4176 _LIBCPP_FUNC_VIS wstring to_wstring(long __val);
4177 _LIBCPP_FUNC_VIS wstring to_wstring(unsigned long __val);
4178 _LIBCPP_FUNC_VIS wstring to_wstring(long long __val);
4179 _LIBCPP_FUNC_VIS wstring to_wstring(unsigned long long __val);
4180 _LIBCPP_FUNC_VIS wstring to_wstring(float __val);
4181 _LIBCPP_FUNC_VIS wstring to_wstring(double __val);
4182 _LIBCPP_FUNC_VIS wstring to_wstring(long double __val);
4184 template<class _CharT, class _Traits, class _Allocator>
4185 const typename basic_string<_CharT, _Traits, _Allocator>::size_type
4186 basic_string<_CharT, _Traits, _Allocator>::npos;
4188 template<class _CharT, class _Traits, class _Allocator>
4189 struct _LIBCPP_TYPE_VIS_ONLY hash<basic_string<_CharT, _Traits, _Allocator> >
4190 : public unary_function<basic_string<_CharT, _Traits, _Allocator>, size_t>
4193 operator()(const basic_string<_CharT, _Traits, _Allocator>& __val) const _NOEXCEPT;
4196 template<class _CharT, class _Traits, class _Allocator>
4198 hash<basic_string<_CharT, _Traits, _Allocator> >::operator()(
4199 const basic_string<_CharT, _Traits, _Allocator>& __val) const _NOEXCEPT
4201 return __do_string_hash(__val.data(), __val.data() + __val.size());
4204 template<class _CharT, class _Traits, class _Allocator>
4205 basic_ostream<_CharT, _Traits>&
4206 operator<<(basic_ostream<_CharT, _Traits>& __os,
4207 const basic_string<_CharT, _Traits, _Allocator>& __str);
4209 template<class _CharT, class _Traits, class _Allocator>
4210 basic_istream<_CharT, _Traits>&
4211 operator>>(basic_istream<_CharT, _Traits>& __is,
4212 basic_string<_CharT, _Traits, _Allocator>& __str);
4214 template<class _CharT, class _Traits, class _Allocator>
4215 basic_istream<_CharT, _Traits>&
4216 getline(basic_istream<_CharT, _Traits>& __is,
4217 basic_string<_CharT, _Traits, _Allocator>& __str, _CharT __dlm);
4219 template<class _CharT, class _Traits, class _Allocator>
4220 inline _LIBCPP_INLINE_VISIBILITY
4221 basic_istream<_CharT, _Traits>&
4222 getline(basic_istream<_CharT, _Traits>& __is,
4223 basic_string<_CharT, _Traits, _Allocator>& __str);
4225 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
4227 template<class _CharT, class _Traits, class _Allocator>
4228 inline _LIBCPP_INLINE_VISIBILITY
4229 basic_istream<_CharT, _Traits>&
4230 getline(basic_istream<_CharT, _Traits>&& __is,
4231 basic_string<_CharT, _Traits, _Allocator>& __str, _CharT __dlm);
4233 template<class _CharT, class _Traits, class _Allocator>
4234 inline _LIBCPP_INLINE_VISIBILITY
4235 basic_istream<_CharT, _Traits>&
4236 getline(basic_istream<_CharT, _Traits>&& __is,
4237 basic_string<_CharT, _Traits, _Allocator>& __str);
4239 #endif // _LIBCPP_HAS_NO_RVALUE_REFERENCES
4241 #if _LIBCPP_DEBUG_LEVEL >= 2
4243 template<class _CharT, class _Traits, class _Allocator>
4245 basic_string<_CharT, _Traits, _Allocator>::__dereferenceable(const const_iterator* __i) const
4247 return this->data() <= _VSTD::__to_raw_pointer(__i->base()) &&
4248 _VSTD::__to_raw_pointer(__i->base()) < this->data() + this->size();
4251 template<class _CharT, class _Traits, class _Allocator>
4253 basic_string<_CharT, _Traits, _Allocator>::__decrementable(const const_iterator* __i) const
4255 return this->data() < _VSTD::__to_raw_pointer(__i->base()) &&
4256 _VSTD::__to_raw_pointer(__i->base()) <= this->data() + this->size();
4259 template<class _CharT, class _Traits, class _Allocator>
4261 basic_string<_CharT, _Traits, _Allocator>::__addable(const const_iterator* __i, ptrdiff_t __n) const
4263 const value_type* __p = _VSTD::__to_raw_pointer(__i->base()) + __n;
4264 return this->data() <= __p && __p <= this->data() + this->size();
4267 template<class _CharT, class _Traits, class _Allocator>
4269 basic_string<_CharT, _Traits, _Allocator>::__subscriptable(const const_iterator* __i, ptrdiff_t __n) const
4271 const value_type* __p = _VSTD::__to_raw_pointer(__i->base()) + __n;
4272 return this->data() <= __p && __p < this->data() + this->size();
4275 #endif // _LIBCPP_DEBUG_LEVEL >= 2
4277 #if _LIBCPP_STD_VER > 11
4278 // Literal suffixes for basic_string [basic.string.literals]
4279 inline namespace literals
4281 inline namespace string_literals
4283 inline _LIBCPP_INLINE_VISIBILITY
4284 basic_string<char> operator "" s( const char *__str, size_t __len )
4286 return basic_string<char> (__str, __len);
4289 inline _LIBCPP_INLINE_VISIBILITY
4290 basic_string<wchar_t> operator "" s( const wchar_t *__str, size_t __len )
4292 return basic_string<wchar_t> (__str, __len);
4295 inline _LIBCPP_INLINE_VISIBILITY
4296 basic_string<char16_t> operator "" s( const char16_t *__str, size_t __len )
4298 return basic_string<char16_t> (__str, __len);
4301 inline _LIBCPP_INLINE_VISIBILITY
4302 basic_string<char32_t> operator "" s( const char32_t *__str, size_t __len )
4304 return basic_string<char32_t> (__str, __len);
4310 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_TYPE_VIS basic_string<char>)
4311 _LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_TYPE_VIS basic_string<wchar_t>)
4312 _LIBCPP_EXTERN_TEMPLATE(string operator+<char, char_traits<char>, allocator<char> >(char const*, string const&))
4314 _LIBCPP_END_NAMESPACE_STD
4316 #endif // _LIBCPP_STRING