1// -*- C++ -*- 2//===--------------------------- string -----------------------------------===// 3// 4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 5// See https://llvm.org/LICENSE.txt for license information. 6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 7// 8//===----------------------------------------------------------------------===// 9 10#ifndef _LIBCPP_STRING 11#define _LIBCPP_STRING 12 13/* 14 string synopsis 15 16namespace std 17{ 18 19template <class stateT> 20class fpos 21{ 22private: 23 stateT st; 24public: 25 fpos(streamoff = streamoff()); 26 27 operator streamoff() const; 28 29 stateT state() const; 30 void state(stateT); 31 32 fpos& operator+=(streamoff); 33 fpos operator+ (streamoff) const; 34 fpos& operator-=(streamoff); 35 fpos operator- (streamoff) const; 36}; 37 38template <class stateT> streamoff operator-(const fpos<stateT>& x, const fpos<stateT>& y); 39 40template <class stateT> bool operator==(const fpos<stateT>& x, const fpos<stateT>& y); 41template <class stateT> bool operator!=(const fpos<stateT>& x, const fpos<stateT>& y); 42 43template <class charT> 44struct char_traits 45{ 46 typedef charT char_type; 47 typedef ... int_type; 48 typedef streamoff off_type; 49 typedef streampos pos_type; 50 typedef mbstate_t state_type; 51 52 static void assign(char_type& c1, const char_type& c2) noexcept; 53 static constexpr bool eq(char_type c1, char_type c2) noexcept; 54 static constexpr bool lt(char_type c1, char_type c2) noexcept; 55 56 static int compare(const char_type* s1, const char_type* s2, size_t n); 57 static size_t length(const char_type* s); 58 static const char_type* find(const char_type* s, size_t n, const char_type& a); 59 static char_type* move(char_type* s1, const char_type* s2, size_t n); 60 static char_type* copy(char_type* s1, const char_type* s2, size_t n); 61 static char_type* assign(char_type* s, size_t n, char_type a); 62 63 static constexpr int_type not_eof(int_type c) noexcept; 64 static constexpr char_type to_char_type(int_type c) noexcept; 65 static constexpr int_type to_int_type(char_type c) noexcept; 66 static constexpr bool eq_int_type(int_type c1, int_type c2) noexcept; 67 static constexpr int_type eof() noexcept; 68}; 69 70template <> struct char_traits<char>; 71template <> struct char_traits<wchar_t>; 72 73template<class charT, class traits = char_traits<charT>, class Allocator = allocator<charT> > 74class basic_string 75{ 76public: 77// types: 78 typedef traits traits_type; 79 typedef typename traits_type::char_type value_type; 80 typedef Allocator allocator_type; 81 typedef typename allocator_type::size_type size_type; 82 typedef typename allocator_type::difference_type difference_type; 83 typedef typename allocator_type::reference reference; 84 typedef typename allocator_type::const_reference const_reference; 85 typedef typename allocator_type::pointer pointer; 86 typedef typename allocator_type::const_pointer const_pointer; 87 typedef implementation-defined iterator; 88 typedef implementation-defined const_iterator; 89 typedef std::reverse_iterator<iterator> reverse_iterator; 90 typedef std::reverse_iterator<const_iterator> const_reverse_iterator; 91 92 static const size_type npos = -1; 93 94 basic_string() 95 noexcept(is_nothrow_default_constructible<allocator_type>::value); 96 explicit basic_string(const allocator_type& a); 97 basic_string(const basic_string& str); 98 basic_string(basic_string&& str) 99 noexcept(is_nothrow_move_constructible<allocator_type>::value); 100 basic_string(const basic_string& str, size_type pos, 101 const allocator_type& a = allocator_type()); 102 basic_string(const basic_string& str, size_type pos, size_type n, 103 const Allocator& a = Allocator()); 104 template<class T> 105 basic_string(const T& t, size_type pos, size_type n, const Allocator& a = Allocator()); // C++17 106 template <class T> 107 explicit basic_string(const T& t, const Allocator& a = Allocator()); // C++17 108 basic_string(const value_type* s, const allocator_type& a = allocator_type()); 109 basic_string(const value_type* s, size_type n, const allocator_type& a = allocator_type()); 110 basic_string(size_type n, value_type c, const allocator_type& a = allocator_type()); 111 template<class InputIterator> 112 basic_string(InputIterator begin, InputIterator end, 113 const allocator_type& a = allocator_type()); 114 basic_string(initializer_list<value_type>, const Allocator& = Allocator()); 115 basic_string(const basic_string&, const Allocator&); 116 basic_string(basic_string&&, const Allocator&); 117 118 ~basic_string(); 119 120 operator basic_string_view<charT, traits>() const noexcept; 121 122 basic_string& operator=(const basic_string& str); 123 template <class T> 124 basic_string& operator=(const T& t); // C++17 125 basic_string& operator=(basic_string&& str) 126 noexcept( 127 allocator_type::propagate_on_container_move_assignment::value || 128 allocator_type::is_always_equal::value ); // C++17 129 basic_string& operator=(const value_type* s); 130 basic_string& operator=(value_type c); 131 basic_string& operator=(initializer_list<value_type>); 132 133 iterator begin() noexcept; 134 const_iterator begin() const noexcept; 135 iterator end() noexcept; 136 const_iterator end() const noexcept; 137 138 reverse_iterator rbegin() noexcept; 139 const_reverse_iterator rbegin() const noexcept; 140 reverse_iterator rend() noexcept; 141 const_reverse_iterator rend() const noexcept; 142 143 const_iterator cbegin() const noexcept; 144 const_iterator cend() const noexcept; 145 const_reverse_iterator crbegin() const noexcept; 146 const_reverse_iterator crend() const noexcept; 147 148 size_type size() const noexcept; 149 size_type length() const noexcept; 150 size_type max_size() const noexcept; 151 size_type capacity() const noexcept; 152 153 void resize(size_type n, value_type c); 154 void resize(size_type n); 155 156 void reserve(size_type res_arg); 157 void reserve(); // deprecated in C++20 158 void shrink_to_fit(); 159 void clear() noexcept; 160 bool empty() const noexcept; 161 162 const_reference operator[](size_type pos) const; 163 reference operator[](size_type pos); 164 165 const_reference at(size_type n) const; 166 reference at(size_type n); 167 168 basic_string& operator+=(const basic_string& str); 169 template <class T> 170 basic_string& operator+=(const T& t); // C++17 171 basic_string& operator+=(const value_type* s); 172 basic_string& operator+=(value_type c); 173 basic_string& operator+=(initializer_list<value_type>); 174 175 basic_string& append(const basic_string& str); 176 template <class T> 177 basic_string& append(const T& t); // C++17 178 basic_string& append(const basic_string& str, size_type pos, size_type n=npos); //C++14 179 template <class T> 180 basic_string& append(const T& t, size_type pos, size_type n=npos); // C++17 181 basic_string& append(const value_type* s, size_type n); 182 basic_string& append(const value_type* s); 183 basic_string& append(size_type n, value_type c); 184 template<class InputIterator> 185 basic_string& append(InputIterator first, InputIterator last); 186 basic_string& append(initializer_list<value_type>); 187 188 void push_back(value_type c); 189 void pop_back(); 190 reference front(); 191 const_reference front() const; 192 reference back(); 193 const_reference back() const; 194 195 basic_string& assign(const basic_string& str); 196 template <class T> 197 basic_string& assign(const T& t); // C++17 198 basic_string& assign(basic_string&& str); 199 basic_string& assign(const basic_string& str, size_type pos, size_type n=npos); // C++14 200 template <class T> 201 basic_string& assign(const T& t, size_type pos, size_type n=npos); // C++17 202 basic_string& assign(const value_type* s, size_type n); 203 basic_string& assign(const value_type* s); 204 basic_string& assign(size_type n, value_type c); 205 template<class InputIterator> 206 basic_string& assign(InputIterator first, InputIterator last); 207 basic_string& assign(initializer_list<value_type>); 208 209 basic_string& insert(size_type pos1, const basic_string& str); 210 template <class T> 211 basic_string& insert(size_type pos1, const T& t); 212 basic_string& insert(size_type pos1, const basic_string& str, 213 size_type pos2, size_type n); 214 template <class T> 215 basic_string& insert(size_type pos1, const T& t, size_type pos2, size_type n); // C++17 216 basic_string& insert(size_type pos, const value_type* s, size_type n=npos); //C++14 217 basic_string& insert(size_type pos, const value_type* s); 218 basic_string& insert(size_type pos, size_type n, value_type c); 219 iterator insert(const_iterator p, value_type c); 220 iterator insert(const_iterator p, size_type n, value_type c); 221 template<class InputIterator> 222 iterator insert(const_iterator p, InputIterator first, InputIterator last); 223 iterator insert(const_iterator p, initializer_list<value_type>); 224 225 basic_string& erase(size_type pos = 0, size_type n = npos); 226 iterator erase(const_iterator position); 227 iterator erase(const_iterator first, const_iterator last); 228 229 basic_string& replace(size_type pos1, size_type n1, const basic_string& str); 230 template <class T> 231 basic_string& replace(size_type pos1, size_type n1, const T& t); // C++17 232 basic_string& replace(size_type pos1, size_type n1, const basic_string& str, 233 size_type pos2, size_type n2=npos); // C++14 234 template <class T> 235 basic_string& replace(size_type pos1, size_type n1, const T& t, 236 size_type pos2, size_type n); // C++17 237 basic_string& replace(size_type pos, size_type n1, const value_type* s, size_type n2); 238 basic_string& replace(size_type pos, size_type n1, const value_type* s); 239 basic_string& replace(size_type pos, size_type n1, size_type n2, value_type c); 240 basic_string& replace(const_iterator i1, const_iterator i2, const basic_string& str); 241 template <class T> 242 basic_string& replace(const_iterator i1, const_iterator i2, const T& t); // C++17 243 basic_string& replace(const_iterator i1, const_iterator i2, const value_type* s, size_type n); 244 basic_string& replace(const_iterator i1, const_iterator i2, const value_type* s); 245 basic_string& replace(const_iterator i1, const_iterator i2, size_type n, value_type c); 246 template<class InputIterator> 247 basic_string& replace(const_iterator i1, const_iterator i2, InputIterator j1, InputIterator j2); 248 basic_string& replace(const_iterator i1, const_iterator i2, initializer_list<value_type>); 249 250 size_type copy(value_type* s, size_type n, size_type pos = 0) const; 251 basic_string substr(size_type pos = 0, size_type n = npos) const; 252 253 void swap(basic_string& str) 254 noexcept(allocator_traits<allocator_type>::propagate_on_container_swap::value || 255 allocator_traits<allocator_type>::is_always_equal::value); // C++17 256 257 const value_type* c_str() const noexcept; 258 const value_type* data() const noexcept; 259 value_type* data() noexcept; // C++17 260 261 allocator_type get_allocator() const noexcept; 262 263 size_type find(const basic_string& str, size_type pos = 0) const noexcept; 264 template <class T> 265 size_type find(const T& t, size_type pos = 0) const; // C++17 266 size_type find(const value_type* s, size_type pos, size_type n) const noexcept; 267 size_type find(const value_type* s, size_type pos = 0) const noexcept; 268 size_type find(value_type c, size_type pos = 0) const noexcept; 269 270 size_type rfind(const basic_string& str, size_type pos = npos) const noexcept; 271 template <class T> 272 size_type rfind(const T& t, size_type pos = npos) const; // C++17 273 size_type rfind(const value_type* s, size_type pos, size_type n) const noexcept; 274 size_type rfind(const value_type* s, size_type pos = npos) const noexcept; 275 size_type rfind(value_type c, size_type pos = npos) const noexcept; 276 277 size_type find_first_of(const basic_string& str, size_type pos = 0) const noexcept; 278 template <class T> 279 size_type find_first_of(const T& t, size_type pos = 0) const; // C++17 280 size_type find_first_of(const value_type* s, size_type pos, size_type n) const noexcept; 281 size_type find_first_of(const value_type* s, size_type pos = 0) const noexcept; 282 size_type find_first_of(value_type c, size_type pos = 0) const noexcept; 283 284 size_type find_last_of(const basic_string& str, size_type pos = npos) const noexcept; 285 template <class T> 286 size_type find_last_of(const T& t, size_type pos = npos) const noexcept; // C++17 287 size_type find_last_of(const value_type* s, size_type pos, size_type n) const noexcept; 288 size_type find_last_of(const value_type* s, size_type pos = npos) const noexcept; 289 size_type find_last_of(value_type c, size_type pos = npos) const noexcept; 290 291 size_type find_first_not_of(const basic_string& str, size_type pos = 0) const noexcept; 292 template <class T> 293 size_type find_first_not_of(const T& t, size_type pos = 0) const; // C++17 294 size_type find_first_not_of(const value_type* s, size_type pos, size_type n) const noexcept; 295 size_type find_first_not_of(const value_type* s, size_type pos = 0) const noexcept; 296 size_type find_first_not_of(value_type c, size_type pos = 0) const noexcept; 297 298 size_type find_last_not_of(const basic_string& str, size_type pos = npos) const noexcept; 299 template <class T> 300 size_type find_last_not_of(const T& t, size_type pos = npos) const; // C++17 301 size_type find_last_not_of(const value_type* s, size_type pos, size_type n) const noexcept; 302 size_type find_last_not_of(const value_type* s, size_type pos = npos) const noexcept; 303 size_type find_last_not_of(value_type c, size_type pos = npos) const noexcept; 304 305 int compare(const basic_string& str) const noexcept; 306 template <class T> 307 int compare(const T& t) const noexcept; // C++17 308 int compare(size_type pos1, size_type n1, const basic_string& str) const; 309 template <class T> 310 int compare(size_type pos1, size_type n1, const T& t) const; // C++17 311 int compare(size_type pos1, size_type n1, const basic_string& str, 312 size_type pos2, size_type n2=npos) const; // C++14 313 template <class T> 314 int compare(size_type pos1, size_type n1, const T& t, 315 size_type pos2, size_type n2=npos) const; // C++17 316 int compare(const value_type* s) const noexcept; 317 int compare(size_type pos1, size_type n1, const value_type* s) const; 318 int compare(size_type pos1, size_type n1, const value_type* s, size_type n2) const; 319 320 bool starts_with(basic_string_view<charT, traits> sv) const noexcept; // C++2a 321 bool starts_with(charT c) const noexcept; // C++2a 322 bool starts_with(const charT* s) const; // C++2a 323 bool ends_with(basic_string_view<charT, traits> sv) const noexcept; // C++2a 324 bool ends_with(charT c) const noexcept; // C++2a 325 bool ends_with(const charT* s) const; // C++2a 326 327 bool __invariants() const; 328}; 329 330template<class InputIterator, 331 class Allocator = allocator<typename iterator_traits<InputIterator>::value_type>> 332basic_string(InputIterator, InputIterator, Allocator = Allocator()) 333 -> basic_string<typename iterator_traits<InputIterator>::value_type, 334 char_traits<typename iterator_traits<InputIterator>::value_type>, 335 Allocator>; // C++17 336 337template<class charT, class traits, class Allocator> 338basic_string<charT, traits, Allocator> 339operator+(const basic_string<charT, traits, Allocator>& lhs, 340 const basic_string<charT, traits, Allocator>& rhs); 341 342template<class charT, class traits, class Allocator> 343basic_string<charT, traits, Allocator> 344operator+(const charT* lhs , const basic_string<charT,traits,Allocator>&rhs); 345 346template<class charT, class traits, class Allocator> 347basic_string<charT, traits, Allocator> 348operator+(charT lhs, const basic_string<charT,traits,Allocator>& rhs); 349 350template<class charT, class traits, class Allocator> 351basic_string<charT, traits, Allocator> 352operator+(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs); 353 354template<class charT, class traits, class Allocator> 355basic_string<charT, traits, Allocator> 356operator+(const basic_string<charT, traits, Allocator>& lhs, charT rhs); 357 358template<class charT, class traits, class Allocator> 359bool operator==(const basic_string<charT, traits, Allocator>& lhs, 360 const basic_string<charT, traits, Allocator>& rhs) noexcept; 361 362template<class charT, class traits, class Allocator> 363bool operator==(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept; 364 365template<class charT, class traits, class Allocator> 366bool operator==(const basic_string<charT,traits,Allocator>& lhs, const charT* rhs) noexcept; 367 368template<class charT, class traits, class Allocator> 369bool operator!=(const basic_string<charT,traits,Allocator>& lhs, 370 const basic_string<charT, traits, Allocator>& rhs) noexcept; 371 372template<class charT, class traits, class Allocator> 373bool operator!=(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept; 374 375template<class charT, class traits, class Allocator> 376bool operator!=(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept; 377 378template<class charT, class traits, class Allocator> 379bool operator< (const basic_string<charT, traits, Allocator>& lhs, 380 const basic_string<charT, traits, Allocator>& rhs) noexcept; 381 382template<class charT, class traits, class Allocator> 383bool operator< (const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept; 384 385template<class charT, class traits, class Allocator> 386bool operator< (const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept; 387 388template<class charT, class traits, class Allocator> 389bool operator> (const basic_string<charT, traits, Allocator>& lhs, 390 const basic_string<charT, traits, Allocator>& rhs) noexcept; 391 392template<class charT, class traits, class Allocator> 393bool operator> (const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept; 394 395template<class charT, class traits, class Allocator> 396bool operator> (const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept; 397 398template<class charT, class traits, class Allocator> 399bool operator<=(const basic_string<charT, traits, Allocator>& lhs, 400 const basic_string<charT, traits, Allocator>& rhs) noexcept; 401 402template<class charT, class traits, class Allocator> 403bool operator<=(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept; 404 405template<class charT, class traits, class Allocator> 406bool operator<=(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept; 407 408template<class charT, class traits, class Allocator> 409bool operator>=(const basic_string<charT, traits, Allocator>& lhs, 410 const basic_string<charT, traits, Allocator>& rhs) noexcept; 411 412template<class charT, class traits, class Allocator> 413bool operator>=(const basic_string<charT, traits, Allocator>& lhs, const charT* rhs) noexcept; 414 415template<class charT, class traits, class Allocator> 416bool operator>=(const charT* lhs, const basic_string<charT, traits, Allocator>& rhs) noexcept; 417 418template<class charT, class traits, class Allocator> 419void swap(basic_string<charT, traits, Allocator>& lhs, 420 basic_string<charT, traits, Allocator>& rhs) 421 noexcept(noexcept(lhs.swap(rhs))); 422 423template<class charT, class traits, class Allocator> 424basic_istream<charT, traits>& 425operator>>(basic_istream<charT, traits>& is, basic_string<charT, traits, Allocator>& str); 426 427template<class charT, class traits, class Allocator> 428basic_ostream<charT, traits>& 429operator<<(basic_ostream<charT, traits>& os, const basic_string<charT, traits, Allocator>& str); 430 431template<class charT, class traits, class Allocator> 432basic_istream<charT, traits>& 433getline(basic_istream<charT, traits>& is, basic_string<charT, traits, Allocator>& str, 434 charT delim); 435 436template<class charT, class traits, class Allocator> 437basic_istream<charT, traits>& 438getline(basic_istream<charT, traits>& is, basic_string<charT, traits, Allocator>& str); 439 440template<class charT, class traits, class Allocator, class U> 441typename basic_string<charT, traits, Allocator>::size_type 442erase(basic_string<charT, traits, Allocator>& c, const U& value); // C++20 443template<class charT, class traits, class Allocator, class Predicate> 444typename basic_string<charT, traits, Allocator>::size_type 445erase_if(basic_string<charT, traits, Allocator>& c, Predicate pred); // C++20 446 447typedef basic_string<char> string; 448typedef basic_string<wchar_t> wstring; 449typedef basic_string<char16_t> u16string; 450typedef basic_string<char32_t> u32string; 451 452int stoi (const string& str, size_t* idx = nullptr, int base = 10); 453long stol (const string& str, size_t* idx = nullptr, int base = 10); 454unsigned long stoul (const string& str, size_t* idx = nullptr, int base = 10); 455long long stoll (const string& str, size_t* idx = nullptr, int base = 10); 456unsigned long long stoull(const string& str, size_t* idx = nullptr, int base = 10); 457 458float stof (const string& str, size_t* idx = nullptr); 459double stod (const string& str, size_t* idx = nullptr); 460long double stold(const string& str, size_t* idx = nullptr); 461 462string to_string(int val); 463string to_string(unsigned val); 464string to_string(long val); 465string to_string(unsigned long val); 466string to_string(long long val); 467string to_string(unsigned long long val); 468string to_string(float val); 469string to_string(double val); 470string to_string(long double val); 471 472int stoi (const wstring& str, size_t* idx = nullptr, int base = 10); 473long stol (const wstring& str, size_t* idx = nullptr, int base = 10); 474unsigned long stoul (const wstring& str, size_t* idx = nullptr, int base = 10); 475long long stoll (const wstring& str, size_t* idx = nullptr, int base = 10); 476unsigned long long stoull(const wstring& str, size_t* idx = nullptr, int base = 10); 477 478float stof (const wstring& str, size_t* idx = nullptr); 479double stod (const wstring& str, size_t* idx = nullptr); 480long double stold(const wstring& str, size_t* idx = nullptr); 481 482wstring to_wstring(int val); 483wstring to_wstring(unsigned val); 484wstring to_wstring(long val); 485wstring to_wstring(unsigned long val); 486wstring to_wstring(long long val); 487wstring to_wstring(unsigned long long val); 488wstring to_wstring(float val); 489wstring to_wstring(double val); 490wstring to_wstring(long double val); 491 492template <> struct hash<string>; 493template <> struct hash<u16string>; 494template <> struct hash<u32string>; 495template <> struct hash<wstring>; 496 497basic_string<char> operator "" s( const char *str, size_t len ); // C++14 498basic_string<wchar_t> operator "" s( const wchar_t *str, size_t len ); // C++14 499basic_string<char16_t> operator "" s( const char16_t *str, size_t len ); // C++14 500basic_string<char32_t> operator "" s( const char32_t *str, size_t len ); // C++14 501 502} // std 503 504*/ 505 506#include <__config> 507#include <string_view> 508#include <iosfwd> 509#include <cstring> 510#include <cstdio> // For EOF. 511#include <cwchar> 512#include <algorithm> 513#include <iterator> 514#include <utility> 515#include <memory> 516#include <stdexcept> 517#include <type_traits> 518#include <initializer_list> 519#include <__functional_base> 520#include <version> 521#ifndef _LIBCPP_HAS_NO_UNICODE_CHARS 522#include <cstdint> 523#endif 524 525#include <__debug> 526 527#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 528#pragma GCC system_header 529#endif 530 531_LIBCPP_PUSH_MACROS 532#include <__undef_macros> 533 534 535_LIBCPP_BEGIN_NAMESPACE_STD 536 537// fpos 538 539template <class _StateT> 540class _LIBCPP_TEMPLATE_VIS fpos 541{ 542private: 543 _StateT __st_; 544 streamoff __off_; 545public: 546 _LIBCPP_INLINE_VISIBILITY fpos(streamoff __off = streamoff()) : __st_(), __off_(__off) {} 547 548 _LIBCPP_INLINE_VISIBILITY operator streamoff() const {return __off_;} 549 550 _LIBCPP_INLINE_VISIBILITY _StateT state() const {return __st_;} 551 _LIBCPP_INLINE_VISIBILITY void state(_StateT __st) {__st_ = __st;} 552 553 _LIBCPP_INLINE_VISIBILITY fpos& operator+=(streamoff __off) {__off_ += __off; return *this;} 554 _LIBCPP_INLINE_VISIBILITY fpos operator+ (streamoff __off) const {fpos __t(*this); __t += __off; return __t;} 555 _LIBCPP_INLINE_VISIBILITY fpos& operator-=(streamoff __off) {__off_ -= __off; return *this;} 556 _LIBCPP_INLINE_VISIBILITY fpos operator- (streamoff __off) const {fpos __t(*this); __t -= __off; return __t;} 557}; 558 559template <class _StateT> 560inline _LIBCPP_INLINE_VISIBILITY 561streamoff operator-(const fpos<_StateT>& __x, const fpos<_StateT>& __y) 562 {return streamoff(__x) - streamoff(__y);} 563 564template <class _StateT> 565inline _LIBCPP_INLINE_VISIBILITY 566bool operator==(const fpos<_StateT>& __x, const fpos<_StateT>& __y) 567 {return streamoff(__x) == streamoff(__y);} 568 569template <class _StateT> 570inline _LIBCPP_INLINE_VISIBILITY 571bool operator!=(const fpos<_StateT>& __x, const fpos<_StateT>& __y) 572 {return streamoff(__x) != streamoff(__y);} 573 574// basic_string 575 576template<class _CharT, class _Traits, class _Allocator> 577basic_string<_CharT, _Traits, _Allocator> 578operator+(const basic_string<_CharT, _Traits, _Allocator>& __x, 579 const basic_string<_CharT, _Traits, _Allocator>& __y); 580 581template<class _CharT, class _Traits, class _Allocator> 582basic_string<_CharT, _Traits, _Allocator> 583operator+(const _CharT* __x, const basic_string<_CharT,_Traits,_Allocator>& __y); 584 585template<class _CharT, class _Traits, class _Allocator> 586basic_string<_CharT, _Traits, _Allocator> 587operator+(_CharT __x, const basic_string<_CharT,_Traits,_Allocator>& __y); 588 589template<class _CharT, class _Traits, class _Allocator> 590inline _LIBCPP_INLINE_VISIBILITY 591basic_string<_CharT, _Traits, _Allocator> 592operator+(const basic_string<_CharT, _Traits, _Allocator>& __x, const _CharT* __y); 593 594template<class _CharT, class _Traits, class _Allocator> 595basic_string<_CharT, _Traits, _Allocator> 596operator+(const basic_string<_CharT, _Traits, _Allocator>& __x, _CharT __y); 597 598_LIBCPP_EXTERN_TEMPLATE(_LIBCPP_FUNC_VIS string operator+<char, char_traits<char>, allocator<char> >(char const*, string const&)) 599 600template <bool> 601class _LIBCPP_TEMPLATE_VIS __basic_string_common 602{ 603protected: 604 _LIBCPP_NORETURN void __throw_length_error() const; 605 _LIBCPP_NORETURN void __throw_out_of_range() const; 606}; 607 608template <bool __b> 609void 610__basic_string_common<__b>::__throw_length_error() const 611{ 612 _VSTD::__throw_length_error("basic_string"); 613} 614 615template <bool __b> 616void 617__basic_string_common<__b>::__throw_out_of_range() const 618{ 619 _VSTD::__throw_out_of_range("basic_string"); 620} 621 622_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS __basic_string_common<true>) 623 624#ifdef _LIBCPP_NO_EXCEPTIONS 625template <class _Iter> 626struct __libcpp_string_gets_noexcept_iterator_impl : public true_type {}; 627#elif defined(_LIBCPP_HAS_NO_NOEXCEPT) 628template <class _Iter> 629struct __libcpp_string_gets_noexcept_iterator_impl : public false_type {}; 630#else 631template <class _Iter, bool = __is_cpp17_forward_iterator<_Iter>::value> 632struct __libcpp_string_gets_noexcept_iterator_impl : public _LIBCPP_BOOL_CONSTANT(( 633 noexcept(++(declval<_Iter&>())) && 634 is_nothrow_assignable<_Iter&, _Iter>::value && 635 noexcept(declval<_Iter>() == declval<_Iter>()) && 636 noexcept(*declval<_Iter>()) 637)) {}; 638 639template <class _Iter> 640struct __libcpp_string_gets_noexcept_iterator_impl<_Iter, false> : public false_type {}; 641#endif 642 643 644template <class _Iter> 645struct __libcpp_string_gets_noexcept_iterator 646 : public _LIBCPP_BOOL_CONSTANT(__libcpp_is_trivial_iterator<_Iter>::value || __libcpp_string_gets_noexcept_iterator_impl<_Iter>::value) {}; 647 648template <class _CharT, class _Traits, class _Tp> 649struct __can_be_converted_to_string_view : public _BoolConstant< 650 is_convertible<const _Tp&, basic_string_view<_CharT, _Traits> >::value && 651 !is_convertible<const _Tp&, const _CharT*>::value 652 > {}; 653 654#ifdef _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT 655 656template <class _CharT, size_t = sizeof(_CharT)> 657struct __padding 658{ 659 unsigned char __xx[sizeof(_CharT)-1]; 660}; 661 662template <class _CharT> 663struct __padding<_CharT, 1> 664{ 665}; 666 667#endif // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT 668 669#ifndef _LIBCPP_NO_HAS_CHAR8_T 670typedef basic_string<char8_t> u8string; 671#endif 672 673#ifndef _LIBCPP_HAS_NO_UNICODE_CHARS 674typedef basic_string<char16_t> u16string; 675typedef basic_string<char32_t> u32string; 676#endif // _LIBCPP_HAS_NO_UNICODE_CHARS 677 678template<class _CharT, class _Traits, class _Allocator> 679class 680 _LIBCPP_TEMPLATE_VIS 681#ifndef _LIBCPP_NO_HAS_CHAR8_T 682 _LIBCPP_PREFERRED_NAME(u8string) 683#endif 684#ifndef _LIBCPP_HAS_NO_UNICODE_CHARS 685 _LIBCPP_PREFERRED_NAME(u16string) 686 _LIBCPP_PREFERRED_NAME(u32string) 687#endif 688 basic_string 689 : private __basic_string_common<true> 690{ 691public: 692 typedef basic_string __self; 693 typedef basic_string_view<_CharT, _Traits> __self_view; 694 typedef _Traits traits_type; 695 typedef _CharT value_type; 696 typedef _Allocator allocator_type; 697 typedef allocator_traits<allocator_type> __alloc_traits; 698 typedef typename __alloc_traits::size_type size_type; 699 typedef typename __alloc_traits::difference_type difference_type; 700 typedef value_type& reference; 701 typedef const value_type& const_reference; 702 typedef typename __alloc_traits::pointer pointer; 703 typedef typename __alloc_traits::const_pointer const_pointer; 704 705 static_assert((!is_array<value_type>::value), "Character type of basic_string must not be an array"); 706 static_assert(( is_standard_layout<value_type>::value), "Character type of basic_string must be standard-layout"); 707 static_assert(( is_trivial<value_type>::value), "Character type of basic_string must be trivial"); 708 static_assert(( is_same<_CharT, typename traits_type::char_type>::value), 709 "traits_type::char_type must be the same type as CharT"); 710 static_assert(( is_same<typename allocator_type::value_type, value_type>::value), 711 "Allocator::value_type must be same type as value_type"); 712 713 typedef __wrap_iter<pointer> iterator; 714 typedef __wrap_iter<const_pointer> const_iterator; 715 typedef _VSTD::reverse_iterator<iterator> reverse_iterator; 716 typedef _VSTD::reverse_iterator<const_iterator> const_reverse_iterator; 717 718private: 719 720#ifdef _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT 721 722 struct __long 723 { 724 pointer __data_; 725 size_type __size_; 726 size_type __cap_; 727 }; 728 729#ifdef _LIBCPP_BIG_ENDIAN 730 static const size_type __short_mask = 0x01; 731 static const size_type __long_mask = 0x1ul; 732#else // _LIBCPP_BIG_ENDIAN 733 static const size_type __short_mask = 0x80; 734 static const size_type __long_mask = ~(size_type(~0) >> 1); 735#endif // _LIBCPP_BIG_ENDIAN 736 737 enum {__min_cap = (sizeof(__long) - 1)/sizeof(value_type) > 2 ? 738 (sizeof(__long) - 1)/sizeof(value_type) : 2}; 739 740 struct __short 741 { 742 value_type __data_[__min_cap]; 743 struct 744 : __padding<value_type> 745 { 746 unsigned char __size_; 747 }; 748 }; 749 750#else 751 752 struct __long 753 { 754 size_type __cap_; 755 size_type __size_; 756 pointer __data_; 757 }; 758 759#ifdef _LIBCPP_BIG_ENDIAN 760 static const size_type __short_mask = 0x80; 761 static const size_type __long_mask = ~(size_type(~0) >> 1); 762#else // _LIBCPP_BIG_ENDIAN 763 static const size_type __short_mask = 0x01; 764 static const size_type __long_mask = 0x1ul; 765#endif // _LIBCPP_BIG_ENDIAN 766 767 enum {__min_cap = (sizeof(__long) - 1)/sizeof(value_type) > 2 ? 768 (sizeof(__long) - 1)/sizeof(value_type) : 2}; 769 770 struct __short 771 { 772 union 773 { 774 unsigned char __size_; 775 value_type __lx; 776 }; 777 value_type __data_[__min_cap]; 778 }; 779 780#endif // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT 781 782 union __ulx{__long __lx; __short __lxx;}; 783 784 enum {__n_words = sizeof(__ulx) / sizeof(size_type)}; 785 786 struct __raw 787 { 788 size_type __words[__n_words]; 789 }; 790 791 struct __rep 792 { 793 union 794 { 795 __long __l; 796 __short __s; 797 __raw __r; 798 }; 799 }; 800 801 __compressed_pair<__rep, allocator_type> __r_; 802 803public: 804 _LIBCPP_FUNC_VIS 805 static const size_type npos = -1; 806 807 _LIBCPP_INLINE_VISIBILITY basic_string() 808 _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value); 809 810 _LIBCPP_INLINE_VISIBILITY explicit basic_string(const allocator_type& __a) 811#if _LIBCPP_STD_VER <= 14 812 _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value); 813#else 814 _NOEXCEPT; 815#endif 816 817 basic_string(const basic_string& __str); 818 basic_string(const basic_string& __str, const allocator_type& __a); 819 820#ifndef _LIBCPP_CXX03_LANG 821 _LIBCPP_INLINE_VISIBILITY 822 basic_string(basic_string&& __str) 823#if _LIBCPP_STD_VER <= 14 824 _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value); 825#else 826 _NOEXCEPT; 827#endif 828 829 _LIBCPP_INLINE_VISIBILITY 830 basic_string(basic_string&& __str, const allocator_type& __a); 831#endif // _LIBCPP_CXX03_LANG 832 833 template <class = _EnableIf<__is_allocator<_Allocator>::value, nullptr_t> > 834 _LIBCPP_INLINE_VISIBILITY 835 basic_string(const _CharT* __s) : __r_(__default_init_tag(), __default_init_tag()) { 836 _LIBCPP_ASSERT(__s != nullptr, "basic_string(const char*) detected nullptr"); 837 __init(__s, traits_type::length(__s)); 838# if _LIBCPP_DEBUG_LEVEL == 2 839 __get_db()->__insert_c(this); 840# endif 841 } 842 843 template <class = _EnableIf<__is_allocator<_Allocator>::value, nullptr_t> > 844 _LIBCPP_INLINE_VISIBILITY 845 basic_string(const _CharT* __s, const _Allocator& __a); 846 847 _LIBCPP_INLINE_VISIBILITY 848 basic_string(const _CharT* __s, size_type __n); 849 _LIBCPP_INLINE_VISIBILITY 850 basic_string(const _CharT* __s, size_type __n, const _Allocator& __a); 851 _LIBCPP_INLINE_VISIBILITY 852 basic_string(size_type __n, _CharT __c); 853 854 template <class = _EnableIf<__is_allocator<_Allocator>::value, nullptr_t> > 855 _LIBCPP_INLINE_VISIBILITY 856 basic_string(size_type __n, _CharT __c, const _Allocator& __a); 857 858 basic_string(const basic_string& __str, size_type __pos, size_type __n, 859 const _Allocator& __a = _Allocator()); 860 _LIBCPP_INLINE_VISIBILITY 861 basic_string(const basic_string& __str, size_type __pos, 862 const _Allocator& __a = _Allocator()); 863 864 template<class _Tp, class = _EnableIf<__can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string>::value> > 865 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 866 basic_string(const _Tp& __t, size_type __pos, size_type __n, 867 const allocator_type& __a = allocator_type()); 868 869 template<class _Tp, class = _EnableIf<__can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && 870 !__is_same_uncvref<_Tp, basic_string>::value> > 871 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 872 explicit basic_string(const _Tp& __t); 873 874 template<class _Tp, class = _EnableIf<__can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string>::value> > 875 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 876 explicit basic_string(const _Tp& __t, const allocator_type& __a); 877 878 template<class _InputIterator, class = _EnableIf<__is_cpp17_input_iterator<_InputIterator>::value> > 879 _LIBCPP_INLINE_VISIBILITY 880 basic_string(_InputIterator __first, _InputIterator __last); 881 template<class _InputIterator, class = _EnableIf<__is_cpp17_input_iterator<_InputIterator>::value> > 882 _LIBCPP_INLINE_VISIBILITY 883 basic_string(_InputIterator __first, _InputIterator __last, const allocator_type& __a); 884#ifndef _LIBCPP_CXX03_LANG 885 _LIBCPP_INLINE_VISIBILITY 886 basic_string(initializer_list<_CharT> __il); 887 _LIBCPP_INLINE_VISIBILITY 888 basic_string(initializer_list<_CharT> __il, const _Allocator& __a); 889#endif // _LIBCPP_CXX03_LANG 890 891 inline ~basic_string(); 892 893 _LIBCPP_INLINE_VISIBILITY 894 operator __self_view() const _NOEXCEPT { return __self_view(data(), size()); } 895 896 basic_string& operator=(const basic_string& __str); 897 898 template <class _Tp, class = _EnableIf<__can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string>::value> > 899 basic_string& operator=(const _Tp& __t) 900 {__self_view __sv = __t; return assign(__sv);} 901 902#ifndef _LIBCPP_CXX03_LANG 903 _LIBCPP_INLINE_VISIBILITY 904 basic_string& operator=(basic_string&& __str) 905 _NOEXCEPT_((__noexcept_move_assign_container<_Allocator, __alloc_traits>::value)); 906 _LIBCPP_INLINE_VISIBILITY 907 basic_string& operator=(initializer_list<value_type> __il) {return assign(__il.begin(), __il.size());} 908#endif 909 _LIBCPP_INLINE_VISIBILITY basic_string& operator=(const value_type* __s) {return assign(__s);} 910 basic_string& operator=(value_type __c); 911 912#if _LIBCPP_DEBUG_LEVEL == 2 913 _LIBCPP_INLINE_VISIBILITY 914 iterator begin() _NOEXCEPT 915 {return iterator(this, __get_pointer());} 916 _LIBCPP_INLINE_VISIBILITY 917 const_iterator begin() const _NOEXCEPT 918 {return const_iterator(this, __get_pointer());} 919 _LIBCPP_INLINE_VISIBILITY 920 iterator end() _NOEXCEPT 921 {return iterator(this, __get_pointer() + size());} 922 _LIBCPP_INLINE_VISIBILITY 923 const_iterator end() const _NOEXCEPT 924 {return const_iterator(this, __get_pointer() + size());} 925#else 926 _LIBCPP_INLINE_VISIBILITY 927 iterator begin() _NOEXCEPT 928 {return iterator(__get_pointer());} 929 _LIBCPP_INLINE_VISIBILITY 930 const_iterator begin() const _NOEXCEPT 931 {return const_iterator(__get_pointer());} 932 _LIBCPP_INLINE_VISIBILITY 933 iterator end() _NOEXCEPT 934 {return iterator(__get_pointer() + size());} 935 _LIBCPP_INLINE_VISIBILITY 936 const_iterator end() const _NOEXCEPT 937 {return const_iterator(__get_pointer() + size());} 938#endif // _LIBCPP_DEBUG_LEVEL == 2 939 _LIBCPP_INLINE_VISIBILITY 940 reverse_iterator rbegin() _NOEXCEPT 941 {return reverse_iterator(end());} 942 _LIBCPP_INLINE_VISIBILITY 943 const_reverse_iterator rbegin() const _NOEXCEPT 944 {return const_reverse_iterator(end());} 945 _LIBCPP_INLINE_VISIBILITY 946 reverse_iterator rend() _NOEXCEPT 947 {return reverse_iterator(begin());} 948 _LIBCPP_INLINE_VISIBILITY 949 const_reverse_iterator rend() const _NOEXCEPT 950 {return const_reverse_iterator(begin());} 951 952 _LIBCPP_INLINE_VISIBILITY 953 const_iterator cbegin() const _NOEXCEPT 954 {return begin();} 955 _LIBCPP_INLINE_VISIBILITY 956 const_iterator cend() const _NOEXCEPT 957 {return end();} 958 _LIBCPP_INLINE_VISIBILITY 959 const_reverse_iterator crbegin() const _NOEXCEPT 960 {return rbegin();} 961 _LIBCPP_INLINE_VISIBILITY 962 const_reverse_iterator crend() const _NOEXCEPT 963 {return rend();} 964 965 _LIBCPP_INLINE_VISIBILITY size_type size() const _NOEXCEPT 966 {return __is_long() ? __get_long_size() : __get_short_size();} 967 _LIBCPP_INLINE_VISIBILITY size_type length() const _NOEXCEPT {return size();} 968 _LIBCPP_INLINE_VISIBILITY size_type max_size() const _NOEXCEPT; 969 _LIBCPP_INLINE_VISIBILITY size_type capacity() const _NOEXCEPT 970 {return (__is_long() ? __get_long_cap() 971 : static_cast<size_type>(__min_cap)) - 1;} 972 973 void resize(size_type __n, value_type __c); 974 _LIBCPP_INLINE_VISIBILITY void resize(size_type __n) {resize(__n, value_type());} 975 976 void reserve(size_type __requested_capacity); 977 _LIBCPP_INLINE_VISIBILITY void __resize_default_init(size_type __n); 978 979 _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_INLINE_VISIBILITY 980 void reserve() _NOEXCEPT {shrink_to_fit();} 981 _LIBCPP_INLINE_VISIBILITY 982 void shrink_to_fit() _NOEXCEPT; 983 _LIBCPP_INLINE_VISIBILITY 984 void clear() _NOEXCEPT; 985 _LIBCPP_NODISCARD_AFTER_CXX17 _LIBCPP_INLINE_VISIBILITY 986 bool empty() const _NOEXCEPT {return size() == 0;} 987 988 _LIBCPP_INLINE_VISIBILITY const_reference operator[](size_type __pos) const _NOEXCEPT; 989 _LIBCPP_INLINE_VISIBILITY reference operator[](size_type __pos) _NOEXCEPT; 990 991 const_reference at(size_type __n) const; 992 reference at(size_type __n); 993 994 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(const basic_string& __str) {return append(__str);} 995 996 template <class _Tp> 997 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 998 _EnableIf 999 < 1000 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value 1001 && !__is_same_uncvref<_Tp, basic_string >::value, 1002 basic_string& 1003 > 1004 operator+=(const _Tp& __t) {__self_view __sv = __t; return append(__sv);} 1005 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(const value_type* __s) {return append(__s);} 1006 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(value_type __c) {push_back(__c); return *this;} 1007#ifndef _LIBCPP_CXX03_LANG 1008 _LIBCPP_INLINE_VISIBILITY basic_string& operator+=(initializer_list<value_type> __il) {return append(__il);} 1009#endif // _LIBCPP_CXX03_LANG 1010 1011 _LIBCPP_INLINE_VISIBILITY 1012 basic_string& append(const basic_string& __str); 1013 1014 template <class _Tp> 1015 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1016 _EnableIf< 1017 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value 1018 && !__is_same_uncvref<_Tp, basic_string>::value, 1019 basic_string& 1020 > 1021 append(const _Tp& __t) { __self_view __sv = __t; return append(__sv.data(), __sv.size()); } 1022 basic_string& append(const basic_string& __str, size_type __pos, size_type __n=npos); 1023 1024 template <class _Tp> 1025 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1026 _EnableIf 1027 < 1028 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value 1029 && !__is_same_uncvref<_Tp, basic_string>::value, 1030 basic_string& 1031 > 1032 append(const _Tp& __t, size_type __pos, size_type __n=npos); 1033 basic_string& append(const value_type* __s, size_type __n); 1034 basic_string& append(const value_type* __s); 1035 basic_string& append(size_type __n, value_type __c); 1036 1037 _LIBCPP_INLINE_VISIBILITY 1038 void __append_default_init(size_type __n); 1039 1040 template <class _ForwardIterator> 1041 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1042 basic_string& __append_forward_unsafe(_ForwardIterator, _ForwardIterator); 1043 template<class _InputIterator> 1044 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1045 _EnableIf 1046 < 1047 __is_exactly_cpp17_input_iterator<_InputIterator>::value 1048 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value, 1049 basic_string& 1050 > 1051 _LIBCPP_INLINE_VISIBILITY 1052 append(_InputIterator __first, _InputIterator __last) { 1053 const basic_string __temp (__first, __last, __alloc()); 1054 append(__temp.data(), __temp.size()); 1055 return *this; 1056 } 1057 template<class _ForwardIterator> 1058 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1059 _EnableIf 1060 < 1061 __is_cpp17_forward_iterator<_ForwardIterator>::value 1062 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value, 1063 basic_string& 1064 > 1065 _LIBCPP_INLINE_VISIBILITY 1066 append(_ForwardIterator __first, _ForwardIterator __last) { 1067 return __append_forward_unsafe(__first, __last); 1068 } 1069 1070#ifndef _LIBCPP_CXX03_LANG 1071 _LIBCPP_INLINE_VISIBILITY 1072 basic_string& append(initializer_list<value_type> __il) {return append(__il.begin(), __il.size());} 1073#endif // _LIBCPP_CXX03_LANG 1074 1075 void push_back(value_type __c); 1076 _LIBCPP_INLINE_VISIBILITY 1077 void pop_back(); 1078 _LIBCPP_INLINE_VISIBILITY reference front() _NOEXCEPT; 1079 _LIBCPP_INLINE_VISIBILITY const_reference front() const _NOEXCEPT; 1080 _LIBCPP_INLINE_VISIBILITY reference back() _NOEXCEPT; 1081 _LIBCPP_INLINE_VISIBILITY const_reference back() const _NOEXCEPT; 1082 1083 template <class _Tp> 1084 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1085 _EnableIf 1086 < 1087 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1088 basic_string& 1089 > 1090 assign(const _Tp & __t) { __self_view __sv = __t; return assign(__sv.data(), __sv.size()); } 1091 _LIBCPP_INLINE_VISIBILITY 1092 basic_string& assign(const basic_string& __str) { return *this = __str; } 1093#ifndef _LIBCPP_CXX03_LANG 1094 _LIBCPP_INLINE_VISIBILITY 1095 basic_string& assign(basic_string&& __str) 1096 _NOEXCEPT_((__noexcept_move_assign_container<_Allocator, __alloc_traits>::value)) 1097 {*this = _VSTD::move(__str); return *this;} 1098#endif 1099 basic_string& assign(const basic_string& __str, size_type __pos, size_type __n=npos); 1100 template <class _Tp> 1101 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1102 _EnableIf 1103 < 1104 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value 1105 && !__is_same_uncvref<_Tp, basic_string>::value, 1106 basic_string& 1107 > 1108 assign(const _Tp & __t, size_type __pos, size_type __n=npos); 1109 basic_string& assign(const value_type* __s, size_type __n); 1110 basic_string& assign(const value_type* __s); 1111 basic_string& assign(size_type __n, value_type __c); 1112 template<class _InputIterator> 1113 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1114 _EnableIf 1115 < 1116 __is_exactly_cpp17_input_iterator<_InputIterator>::value 1117 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value, 1118 basic_string& 1119 > 1120 assign(_InputIterator __first, _InputIterator __last); 1121 template<class _ForwardIterator> 1122 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1123 _EnableIf 1124 < 1125 __is_cpp17_forward_iterator<_ForwardIterator>::value 1126 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value, 1127 basic_string& 1128 > 1129 assign(_ForwardIterator __first, _ForwardIterator __last); 1130#ifndef _LIBCPP_CXX03_LANG 1131 _LIBCPP_INLINE_VISIBILITY 1132 basic_string& assign(initializer_list<value_type> __il) {return assign(__il.begin(), __il.size());} 1133#endif // _LIBCPP_CXX03_LANG 1134 1135 _LIBCPP_INLINE_VISIBILITY 1136 basic_string& insert(size_type __pos1, const basic_string& __str); 1137 1138 template <class _Tp> 1139 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1140 _EnableIf 1141 < 1142 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1143 basic_string& 1144 > 1145 insert(size_type __pos1, const _Tp& __t) 1146 { __self_view __sv = __t; return insert(__pos1, __sv.data(), __sv.size()); } 1147 1148 template <class _Tp> 1149 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1150 _EnableIf 1151 < 1152 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string>::value, 1153 basic_string& 1154 > 1155 insert(size_type __pos1, const _Tp& __t, size_type __pos2, size_type __n=npos); 1156 basic_string& insert(size_type __pos1, const basic_string& __str, size_type __pos2, size_type __n=npos); 1157 basic_string& insert(size_type __pos, const value_type* __s, size_type __n); 1158 basic_string& insert(size_type __pos, const value_type* __s); 1159 basic_string& insert(size_type __pos, size_type __n, value_type __c); 1160 iterator insert(const_iterator __pos, value_type __c); 1161 _LIBCPP_INLINE_VISIBILITY 1162 iterator insert(const_iterator __pos, size_type __n, value_type __c); 1163 template<class _InputIterator> 1164 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1165 _EnableIf 1166 < 1167 __is_exactly_cpp17_input_iterator<_InputIterator>::value 1168 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value, 1169 iterator 1170 > 1171 insert(const_iterator __pos, _InputIterator __first, _InputIterator __last); 1172 template<class _ForwardIterator> 1173 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1174 _EnableIf 1175 < 1176 __is_cpp17_forward_iterator<_ForwardIterator>::value 1177 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value, 1178 iterator 1179 > 1180 insert(const_iterator __pos, _ForwardIterator __first, _ForwardIterator __last); 1181#ifndef _LIBCPP_CXX03_LANG 1182 _LIBCPP_INLINE_VISIBILITY 1183 iterator insert(const_iterator __pos, initializer_list<value_type> __il) 1184 {return insert(__pos, __il.begin(), __il.end());} 1185#endif // _LIBCPP_CXX03_LANG 1186 1187 basic_string& erase(size_type __pos = 0, size_type __n = npos); 1188 _LIBCPP_INLINE_VISIBILITY 1189 iterator erase(const_iterator __pos); 1190 _LIBCPP_INLINE_VISIBILITY 1191 iterator erase(const_iterator __first, const_iterator __last); 1192 1193 _LIBCPP_INLINE_VISIBILITY 1194 basic_string& replace(size_type __pos1, size_type __n1, const basic_string& __str); 1195 1196 template <class _Tp> 1197 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1198 _EnableIf 1199 < 1200 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1201 basic_string& 1202 > 1203 replace(size_type __pos1, size_type __n1, const _Tp& __t) { __self_view __sv = __t; return replace(__pos1, __n1, __sv.data(), __sv.size()); } 1204 basic_string& replace(size_type __pos1, size_type __n1, const basic_string& __str, size_type __pos2, size_type __n2=npos); 1205 template <class _Tp> 1206 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1207 _EnableIf 1208 < 1209 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string>::value, 1210 basic_string& 1211 > 1212 replace(size_type __pos1, size_type __n1, const _Tp& __t, size_type __pos2, size_type __n2=npos); 1213 basic_string& replace(size_type __pos, size_type __n1, const value_type* __s, size_type __n2); 1214 basic_string& replace(size_type __pos, size_type __n1, const value_type* __s); 1215 basic_string& replace(size_type __pos, size_type __n1, size_type __n2, value_type __c); 1216 _LIBCPP_INLINE_VISIBILITY 1217 basic_string& replace(const_iterator __i1, const_iterator __i2, const basic_string& __str); 1218 1219 template <class _Tp> 1220 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1221 _EnableIf 1222 < 1223 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1224 basic_string& 1225 > 1226 replace(const_iterator __i1, const_iterator __i2, const _Tp& __t) { __self_view __sv = __t; return replace(__i1 - begin(), __i2 - __i1, __sv); } 1227 1228 _LIBCPP_INLINE_VISIBILITY 1229 basic_string& replace(const_iterator __i1, const_iterator __i2, const value_type* __s, size_type __n); 1230 _LIBCPP_INLINE_VISIBILITY 1231 basic_string& replace(const_iterator __i1, const_iterator __i2, const value_type* __s); 1232 _LIBCPP_INLINE_VISIBILITY 1233 basic_string& replace(const_iterator __i1, const_iterator __i2, size_type __n, value_type __c); 1234 template<class _InputIterator> 1235 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1236 _EnableIf 1237 < 1238 __is_cpp17_input_iterator<_InputIterator>::value, 1239 basic_string& 1240 > 1241 replace(const_iterator __i1, const_iterator __i2, _InputIterator __j1, _InputIterator __j2); 1242#ifndef _LIBCPP_CXX03_LANG 1243 _LIBCPP_INLINE_VISIBILITY 1244 basic_string& replace(const_iterator __i1, const_iterator __i2, initializer_list<value_type> __il) 1245 {return replace(__i1, __i2, __il.begin(), __il.end());} 1246#endif // _LIBCPP_CXX03_LANG 1247 1248 size_type copy(value_type* __s, size_type __n, size_type __pos = 0) const; 1249 _LIBCPP_INLINE_VISIBILITY 1250 basic_string substr(size_type __pos = 0, size_type __n = npos) const; 1251 1252 _LIBCPP_INLINE_VISIBILITY 1253 void swap(basic_string& __str) 1254#if _LIBCPP_STD_VER >= 14 1255 _NOEXCEPT; 1256#else 1257 _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 1258 __is_nothrow_swappable<allocator_type>::value); 1259#endif 1260 1261 _LIBCPP_INLINE_VISIBILITY 1262 const value_type* c_str() const _NOEXCEPT {return data();} 1263 _LIBCPP_INLINE_VISIBILITY 1264 const value_type* data() const _NOEXCEPT {return _VSTD::__to_address(__get_pointer());} 1265#if _LIBCPP_STD_VER > 14 || defined(_LIBCPP_BUILDING_LIBRARY) 1266 _LIBCPP_INLINE_VISIBILITY 1267 value_type* data() _NOEXCEPT {return _VSTD::__to_address(__get_pointer());} 1268#endif 1269 1270 _LIBCPP_INLINE_VISIBILITY 1271 allocator_type get_allocator() const _NOEXCEPT {return __alloc();} 1272 1273 _LIBCPP_INLINE_VISIBILITY 1274 size_type find(const basic_string& __str, size_type __pos = 0) const _NOEXCEPT; 1275 1276 template <class _Tp> 1277 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1278 _EnableIf 1279 < 1280 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1281 size_type 1282 > 1283 find(const _Tp& __t, size_type __pos = 0) const; 1284 size_type find(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT; 1285 _LIBCPP_INLINE_VISIBILITY 1286 size_type find(const value_type* __s, size_type __pos = 0) const _NOEXCEPT; 1287 size_type find(value_type __c, size_type __pos = 0) const _NOEXCEPT; 1288 1289 _LIBCPP_INLINE_VISIBILITY 1290 size_type rfind(const basic_string& __str, size_type __pos = npos) const _NOEXCEPT; 1291 1292 template <class _Tp> 1293 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1294 _EnableIf 1295 < 1296 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1297 size_type 1298 > 1299 rfind(const _Tp& __t, size_type __pos = npos) const; 1300 size_type rfind(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT; 1301 _LIBCPP_INLINE_VISIBILITY 1302 size_type rfind(const value_type* __s, size_type __pos = npos) const _NOEXCEPT; 1303 size_type rfind(value_type __c, size_type __pos = npos) const _NOEXCEPT; 1304 1305 _LIBCPP_INLINE_VISIBILITY 1306 size_type find_first_of(const basic_string& __str, size_type __pos = 0) const _NOEXCEPT; 1307 1308 template <class _Tp> 1309 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1310 _EnableIf 1311 < 1312 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1313 size_type 1314 > 1315 find_first_of(const _Tp& __t, size_type __pos = 0) const; 1316 size_type find_first_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT; 1317 _LIBCPP_INLINE_VISIBILITY 1318 size_type find_first_of(const value_type* __s, size_type __pos = 0) const _NOEXCEPT; 1319 _LIBCPP_INLINE_VISIBILITY 1320 size_type find_first_of(value_type __c, size_type __pos = 0) const _NOEXCEPT; 1321 1322 _LIBCPP_INLINE_VISIBILITY 1323 size_type find_last_of(const basic_string& __str, size_type __pos = npos) const _NOEXCEPT; 1324 1325 template <class _Tp> 1326 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1327 _EnableIf 1328 < 1329 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1330 size_type 1331 > 1332 find_last_of(const _Tp& __t, size_type __pos = npos) const; 1333 size_type find_last_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT; 1334 _LIBCPP_INLINE_VISIBILITY 1335 size_type find_last_of(const value_type* __s, size_type __pos = npos) const _NOEXCEPT; 1336 _LIBCPP_INLINE_VISIBILITY 1337 size_type find_last_of(value_type __c, size_type __pos = npos) const _NOEXCEPT; 1338 1339 _LIBCPP_INLINE_VISIBILITY 1340 size_type find_first_not_of(const basic_string& __str, size_type __pos = 0) const _NOEXCEPT; 1341 1342 template <class _Tp> 1343 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1344 _EnableIf 1345 < 1346 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1347 size_type 1348 > 1349 find_first_not_of(const _Tp &__t, size_type __pos = 0) const; 1350 size_type find_first_not_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT; 1351 _LIBCPP_INLINE_VISIBILITY 1352 size_type find_first_not_of(const value_type* __s, size_type __pos = 0) const _NOEXCEPT; 1353 _LIBCPP_INLINE_VISIBILITY 1354 size_type find_first_not_of(value_type __c, size_type __pos = 0) const _NOEXCEPT; 1355 1356 _LIBCPP_INLINE_VISIBILITY 1357 size_type find_last_not_of(const basic_string& __str, size_type __pos = npos) const _NOEXCEPT; 1358 1359 template <class _Tp> 1360 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1361 _EnableIf 1362 < 1363 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1364 size_type 1365 > 1366 find_last_not_of(const _Tp& __t, size_type __pos = npos) const; 1367 size_type find_last_not_of(const value_type* __s, size_type __pos, size_type __n) const _NOEXCEPT; 1368 _LIBCPP_INLINE_VISIBILITY 1369 size_type find_last_not_of(const value_type* __s, size_type __pos = npos) const _NOEXCEPT; 1370 _LIBCPP_INLINE_VISIBILITY 1371 size_type find_last_not_of(value_type __c, size_type __pos = npos) const _NOEXCEPT; 1372 1373 _LIBCPP_INLINE_VISIBILITY 1374 int compare(const basic_string& __str) const _NOEXCEPT; 1375 1376 template <class _Tp> 1377 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1378 _EnableIf 1379 < 1380 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1381 int 1382 > 1383 compare(const _Tp &__t) const; 1384 1385 template <class _Tp> 1386 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 1387 _EnableIf 1388 < 1389 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 1390 int 1391 > 1392 compare(size_type __pos1, size_type __n1, const _Tp& __t) const; 1393 1394 _LIBCPP_INLINE_VISIBILITY 1395 int compare(size_type __pos1, size_type __n1, const basic_string& __str) const; 1396 int compare(size_type __pos1, size_type __n1, const basic_string& __str, size_type __pos2, size_type __n2=npos) const; 1397 1398 template <class _Tp> 1399 inline _LIBCPP_INLINE_VISIBILITY 1400 _EnableIf 1401 < 1402 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string>::value, 1403 int 1404 > 1405 compare(size_type __pos1, size_type __n1, const _Tp& __t, size_type __pos2, size_type __n2=npos) const; 1406 int compare(const value_type* __s) const _NOEXCEPT; 1407 int compare(size_type __pos1, size_type __n1, const value_type* __s) const; 1408 int compare(size_type __pos1, size_type __n1, const value_type* __s, size_type __n2) const; 1409 1410#if _LIBCPP_STD_VER > 17 1411 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 1412 bool starts_with(__self_view __sv) const _NOEXCEPT 1413 { return __self_view(data(), size()).starts_with(__sv); } 1414 1415 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 1416 bool starts_with(value_type __c) const _NOEXCEPT 1417 { return !empty() && _Traits::eq(front(), __c); } 1418 1419 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 1420 bool starts_with(const value_type* __s) const _NOEXCEPT 1421 { return starts_with(__self_view(__s)); } 1422 1423 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 1424 bool ends_with(__self_view __sv) const _NOEXCEPT 1425 { return __self_view(data(), size()).ends_with( __sv); } 1426 1427 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 1428 bool ends_with(value_type __c) const _NOEXCEPT 1429 { return !empty() && _Traits::eq(back(), __c); } 1430 1431 _LIBCPP_CONSTEXPR_AFTER_CXX11 _LIBCPP_INLINE_VISIBILITY 1432 bool ends_with(const value_type* __s) const _NOEXCEPT 1433 { return ends_with(__self_view(__s)); } 1434#endif 1435 1436 _LIBCPP_INLINE_VISIBILITY bool __invariants() const; 1437 1438 _LIBCPP_INLINE_VISIBILITY void __clear_and_shrink() _NOEXCEPT; 1439 1440 _LIBCPP_INLINE_VISIBILITY void __shrink_or_extend(size_type __target_capacity); 1441 1442 _LIBCPP_INLINE_VISIBILITY 1443 bool __is_long() const _NOEXCEPT 1444 {return bool(__r_.first().__s.__size_ & __short_mask);} 1445 1446#if _LIBCPP_DEBUG_LEVEL == 2 1447 1448 bool __dereferenceable(const const_iterator* __i) const; 1449 bool __decrementable(const const_iterator* __i) const; 1450 bool __addable(const const_iterator* __i, ptrdiff_t __n) const; 1451 bool __subscriptable(const const_iterator* __i, ptrdiff_t __n) const; 1452 1453#endif // _LIBCPP_DEBUG_LEVEL == 2 1454 1455private: 1456 _LIBCPP_INLINE_VISIBILITY 1457 allocator_type& __alloc() _NOEXCEPT 1458 {return __r_.second();} 1459 _LIBCPP_INLINE_VISIBILITY 1460 const allocator_type& __alloc() const _NOEXCEPT 1461 {return __r_.second();} 1462 1463#ifdef _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT 1464 1465 _LIBCPP_INLINE_VISIBILITY 1466 void __set_short_size(size_type __s) _NOEXCEPT 1467# ifdef _LIBCPP_BIG_ENDIAN 1468 {__r_.first().__s.__size_ = (unsigned char)(__s << 1);} 1469# else 1470 {__r_.first().__s.__size_ = (unsigned char)(__s);} 1471# endif 1472 1473 _LIBCPP_INLINE_VISIBILITY 1474 size_type __get_short_size() const _NOEXCEPT 1475# ifdef _LIBCPP_BIG_ENDIAN 1476 {return __r_.first().__s.__size_ >> 1;} 1477# else 1478 {return __r_.first().__s.__size_;} 1479# endif 1480 1481#else // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT 1482 1483 _LIBCPP_INLINE_VISIBILITY 1484 void __set_short_size(size_type __s) _NOEXCEPT 1485# ifdef _LIBCPP_BIG_ENDIAN 1486 {__r_.first().__s.__size_ = (unsigned char)(__s);} 1487# else 1488 {__r_.first().__s.__size_ = (unsigned char)(__s << 1);} 1489# endif 1490 1491 _LIBCPP_INLINE_VISIBILITY 1492 size_type __get_short_size() const _NOEXCEPT 1493# ifdef _LIBCPP_BIG_ENDIAN 1494 {return __r_.first().__s.__size_;} 1495# else 1496 {return __r_.first().__s.__size_ >> 1;} 1497# endif 1498 1499#endif // _LIBCPP_ABI_ALTERNATE_STRING_LAYOUT 1500 1501 _LIBCPP_INLINE_VISIBILITY 1502 void __set_long_size(size_type __s) _NOEXCEPT 1503 {__r_.first().__l.__size_ = __s;} 1504 _LIBCPP_INLINE_VISIBILITY 1505 size_type __get_long_size() const _NOEXCEPT 1506 {return __r_.first().__l.__size_;} 1507 _LIBCPP_INLINE_VISIBILITY 1508 void __set_size(size_type __s) _NOEXCEPT 1509 {if (__is_long()) __set_long_size(__s); else __set_short_size(__s);} 1510 1511 _LIBCPP_INLINE_VISIBILITY 1512 void __set_long_cap(size_type __s) _NOEXCEPT 1513 {__r_.first().__l.__cap_ = __long_mask | __s;} 1514 _LIBCPP_INLINE_VISIBILITY 1515 size_type __get_long_cap() const _NOEXCEPT 1516 {return __r_.first().__l.__cap_ & size_type(~__long_mask);} 1517 1518 _LIBCPP_INLINE_VISIBILITY 1519 void __set_long_pointer(pointer __p) _NOEXCEPT 1520 {__r_.first().__l.__data_ = __p;} 1521 _LIBCPP_INLINE_VISIBILITY 1522 pointer __get_long_pointer() _NOEXCEPT 1523 {return __r_.first().__l.__data_;} 1524 _LIBCPP_INLINE_VISIBILITY 1525 const_pointer __get_long_pointer() const _NOEXCEPT 1526 {return __r_.first().__l.__data_;} 1527 _LIBCPP_INLINE_VISIBILITY 1528 pointer __get_short_pointer() _NOEXCEPT 1529 {return pointer_traits<pointer>::pointer_to(__r_.first().__s.__data_[0]);} 1530 _LIBCPP_INLINE_VISIBILITY 1531 const_pointer __get_short_pointer() const _NOEXCEPT 1532 {return pointer_traits<const_pointer>::pointer_to(__r_.first().__s.__data_[0]);} 1533 _LIBCPP_INLINE_VISIBILITY 1534 pointer __get_pointer() _NOEXCEPT 1535 {return __is_long() ? __get_long_pointer() : __get_short_pointer();} 1536 _LIBCPP_INLINE_VISIBILITY 1537 const_pointer __get_pointer() const _NOEXCEPT 1538 {return __is_long() ? __get_long_pointer() : __get_short_pointer();} 1539 1540 _LIBCPP_INLINE_VISIBILITY 1541 void __zero() _NOEXCEPT 1542 { 1543 size_type (&__a)[__n_words] = __r_.first().__r.__words; 1544 for (unsigned __i = 0; __i < __n_words; ++__i) 1545 __a[__i] = 0; 1546 } 1547 1548 template <size_type __a> static 1549 _LIBCPP_INLINE_VISIBILITY 1550 size_type __align_it(size_type __s) _NOEXCEPT 1551 {return (__s + (__a-1)) & ~(__a-1);} 1552 enum {__alignment = 16}; 1553 static _LIBCPP_INLINE_VISIBILITY 1554 size_type __recommend(size_type __s) _NOEXCEPT 1555 { 1556 if (__s < __min_cap) return static_cast<size_type>(__min_cap) - 1; 1557 size_type __guess = __align_it<sizeof(value_type) < __alignment ? 1558 __alignment/sizeof(value_type) : 1 > (__s+1) - 1; 1559 if (__guess == __min_cap) ++__guess; 1560 return __guess; 1561 } 1562 1563 inline 1564 void __init(const value_type* __s, size_type __sz, size_type __reserve); 1565 inline 1566 void __init(const value_type* __s, size_type __sz); 1567 inline 1568 void __init(size_type __n, value_type __c); 1569 1570 // Slow path for the (inlined) copy constructor for 'long' strings. 1571 // Always externally instantiated and not inlined. 1572 // Requires that __s is zero terminated. 1573 // The main reason for this function to exist is because for unstable, we 1574 // want to allow inlining of the copy constructor. However, we don't want 1575 // to call the __init() functions as those are marked as inline which may 1576 // result in over-aggressive inlining by the compiler, where our aim is 1577 // to only inline the fast path code directly in the ctor. 1578 void __init_copy_ctor_external(const value_type* __s, size_type __sz); 1579 1580 template <class _InputIterator> 1581 inline 1582 _EnableIf 1583 < 1584 __is_exactly_cpp17_input_iterator<_InputIterator>::value 1585 > 1586 __init(_InputIterator __first, _InputIterator __last); 1587 1588 template <class _ForwardIterator> 1589 inline 1590 _EnableIf 1591 < 1592 __is_cpp17_forward_iterator<_ForwardIterator>::value 1593 > 1594 __init(_ForwardIterator __first, _ForwardIterator __last); 1595 1596 void __grow_by(size_type __old_cap, size_type __delta_cap, size_type __old_sz, 1597 size_type __n_copy, size_type __n_del, size_type __n_add = 0); 1598 void __grow_by_and_replace(size_type __old_cap, size_type __delta_cap, size_type __old_sz, 1599 size_type __n_copy, size_type __n_del, 1600 size_type __n_add, const value_type* __p_new_stuff); 1601 1602 // __assign_no_alias is invoked for assignment operations where we 1603 // have proof that the input does not alias the current instance. 1604 // For example, operator=(basic_string) performs a 'self' check. 1605 template <bool __is_short> 1606 basic_string& __assign_no_alias(const value_type* __s, size_type __n); 1607 1608 _LIBCPP_INLINE_VISIBILITY 1609 void __erase_to_end(size_type __pos); 1610 1611 // __erase_external_with_move is invoked for erase() invocations where 1612 // `n ~= npos`, likely requiring memory moves on the string data. 1613 void __erase_external_with_move(size_type __pos, size_type __n); 1614 1615 _LIBCPP_INLINE_VISIBILITY 1616 void __copy_assign_alloc(const basic_string& __str) 1617 {__copy_assign_alloc(__str, integral_constant<bool, 1618 __alloc_traits::propagate_on_container_copy_assignment::value>());} 1619 1620 _LIBCPP_INLINE_VISIBILITY 1621 void __copy_assign_alloc(const basic_string& __str, true_type) 1622 { 1623 if (__alloc() == __str.__alloc()) 1624 __alloc() = __str.__alloc(); 1625 else 1626 { 1627 if (!__str.__is_long()) 1628 { 1629 __clear_and_shrink(); 1630 __alloc() = __str.__alloc(); 1631 } 1632 else 1633 { 1634 allocator_type __a = __str.__alloc(); 1635 pointer __p = __alloc_traits::allocate(__a, __str.__get_long_cap()); 1636 __clear_and_shrink(); 1637 __alloc() = _VSTD::move(__a); 1638 __set_long_pointer(__p); 1639 __set_long_cap(__str.__get_long_cap()); 1640 __set_long_size(__str.size()); 1641 } 1642 } 1643 } 1644 1645 _LIBCPP_INLINE_VISIBILITY 1646 void __copy_assign_alloc(const basic_string&, false_type) _NOEXCEPT 1647 {} 1648 1649#ifndef _LIBCPP_CXX03_LANG 1650 _LIBCPP_INLINE_VISIBILITY 1651 void __move_assign(basic_string& __str, false_type) 1652 _NOEXCEPT_(__alloc_traits::is_always_equal::value); 1653 _LIBCPP_INLINE_VISIBILITY 1654 void __move_assign(basic_string& __str, true_type) 1655#if _LIBCPP_STD_VER > 14 1656 _NOEXCEPT; 1657#else 1658 _NOEXCEPT_(is_nothrow_move_assignable<allocator_type>::value); 1659#endif 1660#endif 1661 1662 _LIBCPP_INLINE_VISIBILITY 1663 void 1664 __move_assign_alloc(basic_string& __str) 1665 _NOEXCEPT_( 1666 !__alloc_traits::propagate_on_container_move_assignment::value || 1667 is_nothrow_move_assignable<allocator_type>::value) 1668 {__move_assign_alloc(__str, integral_constant<bool, 1669 __alloc_traits::propagate_on_container_move_assignment::value>());} 1670 1671 _LIBCPP_INLINE_VISIBILITY 1672 void __move_assign_alloc(basic_string& __c, true_type) 1673 _NOEXCEPT_(is_nothrow_move_assignable<allocator_type>::value) 1674 { 1675 __alloc() = _VSTD::move(__c.__alloc()); 1676 } 1677 1678 _LIBCPP_INLINE_VISIBILITY 1679 void __move_assign_alloc(basic_string&, false_type) 1680 _NOEXCEPT 1681 {} 1682 1683 basic_string& __assign_external(const value_type* __s); 1684 basic_string& __assign_external(const value_type* __s, size_type __n); 1685 1686 // Assigns the value in __s, guaranteed to be __n < __min_cap in length. 1687 inline basic_string& __assign_short(const value_type* __s, size_type __n) { 1688 pointer __p = __is_long() 1689 ? (__set_long_size(__n), __get_long_pointer()) 1690 : (__set_short_size(__n), __get_short_pointer()); 1691 traits_type::move(_VSTD::__to_address(__p), __s, __n); 1692 traits_type::assign(__p[__n], value_type()); 1693 return *this; 1694 } 1695 1696 _LIBCPP_INLINE_VISIBILITY void __invalidate_all_iterators(); 1697 _LIBCPP_INLINE_VISIBILITY void __invalidate_iterators_past(size_type); 1698 1699 friend basic_string operator+<>(const basic_string&, const basic_string&); 1700 friend basic_string operator+<>(const value_type*, const basic_string&); 1701 friend basic_string operator+<>(value_type, const basic_string&); 1702 friend basic_string operator+<>(const basic_string&, const value_type*); 1703 friend basic_string operator+<>(const basic_string&, value_type); 1704}; 1705 1706// These declarations must appear before any functions are implicitly used 1707// so that they have the correct visibility specifier. 1708#ifdef _LIBCPP_ABI_STRING_OPTIMIZED_EXTERNAL_INSTANTIATION 1709_LIBCPP_STRING_UNSTABLE_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE, char) 1710_LIBCPP_STRING_UNSTABLE_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE, wchar_t) 1711#else 1712_LIBCPP_STRING_V1_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE, char) 1713_LIBCPP_STRING_V1_EXTERN_TEMPLATE_LIST(_LIBCPP_EXTERN_TEMPLATE, wchar_t) 1714#endif 1715 1716 1717#ifndef _LIBCPP_HAS_NO_DEDUCTION_GUIDES 1718template<class _InputIterator, 1719 class _CharT = typename iterator_traits<_InputIterator>::value_type, 1720 class _Allocator = allocator<_CharT>, 1721 class = _EnableIf<__is_cpp17_input_iterator<_InputIterator>::value>, 1722 class = _EnableIf<__is_allocator<_Allocator>::value> 1723 > 1724basic_string(_InputIterator, _InputIterator, _Allocator = _Allocator()) 1725 -> basic_string<_CharT, char_traits<_CharT>, _Allocator>; 1726 1727template<class _CharT, 1728 class _Traits, 1729 class _Allocator = allocator<_CharT>, 1730 class = _EnableIf<__is_allocator<_Allocator>::value> 1731 > 1732explicit basic_string(basic_string_view<_CharT, _Traits>, const _Allocator& = _Allocator()) 1733 -> basic_string<_CharT, _Traits, _Allocator>; 1734 1735template<class _CharT, 1736 class _Traits, 1737 class _Allocator = allocator<_CharT>, 1738 class = _EnableIf<__is_allocator<_Allocator>::value>, 1739 class _Sz = typename allocator_traits<_Allocator>::size_type 1740 > 1741basic_string(basic_string_view<_CharT, _Traits>, _Sz, _Sz, const _Allocator& = _Allocator()) 1742 -> basic_string<_CharT, _Traits, _Allocator>; 1743#endif 1744 1745template <class _CharT, class _Traits, class _Allocator> 1746inline 1747void 1748basic_string<_CharT, _Traits, _Allocator>::__invalidate_all_iterators() 1749{ 1750#if _LIBCPP_DEBUG_LEVEL == 2 1751 __get_db()->__invalidate_all(this); 1752#endif 1753} 1754 1755template <class _CharT, class _Traits, class _Allocator> 1756inline 1757void 1758basic_string<_CharT, _Traits, _Allocator>::__invalidate_iterators_past(size_type 1759#if _LIBCPP_DEBUG_LEVEL == 2 1760 __pos 1761#endif 1762 ) 1763{ 1764#if _LIBCPP_DEBUG_LEVEL == 2 1765 __c_node* __c = __get_db()->__find_c_and_lock(this); 1766 if (__c) 1767 { 1768 const_pointer __new_last = __get_pointer() + __pos; 1769 for (__i_node** __p = __c->end_; __p != __c->beg_; ) 1770 { 1771 --__p; 1772 const_iterator* __i = static_cast<const_iterator*>((*__p)->__i_); 1773 if (__i->base() > __new_last) 1774 { 1775 (*__p)->__c_ = nullptr; 1776 if (--__c->end_ != __p) 1777 _VSTD::memmove(__p, __p+1, (__c->end_ - __p)*sizeof(__i_node*)); 1778 } 1779 } 1780 __get_db()->unlock(); 1781 } 1782#endif // _LIBCPP_DEBUG_LEVEL == 2 1783} 1784 1785template <class _CharT, class _Traits, class _Allocator> 1786inline 1787basic_string<_CharT, _Traits, _Allocator>::basic_string() 1788 _NOEXCEPT_(is_nothrow_default_constructible<allocator_type>::value) 1789 : __r_(__default_init_tag(), __default_init_tag()) 1790{ 1791#if _LIBCPP_DEBUG_LEVEL == 2 1792 __get_db()->__insert_c(this); 1793#endif 1794 __zero(); 1795} 1796 1797template <class _CharT, class _Traits, class _Allocator> 1798inline 1799basic_string<_CharT, _Traits, _Allocator>::basic_string(const allocator_type& __a) 1800#if _LIBCPP_STD_VER <= 14 1801 _NOEXCEPT_(is_nothrow_copy_constructible<allocator_type>::value) 1802#else 1803 _NOEXCEPT 1804#endif 1805: __r_(__default_init_tag(), __a) 1806{ 1807#if _LIBCPP_DEBUG_LEVEL == 2 1808 __get_db()->__insert_c(this); 1809#endif 1810 __zero(); 1811} 1812 1813template <class _CharT, class _Traits, class _Allocator> 1814void basic_string<_CharT, _Traits, _Allocator>::__init(const value_type* __s, 1815 size_type __sz, 1816 size_type __reserve) 1817{ 1818 if (__reserve > max_size()) 1819 this->__throw_length_error(); 1820 pointer __p; 1821 if (__reserve < __min_cap) 1822 { 1823 __set_short_size(__sz); 1824 __p = __get_short_pointer(); 1825 } 1826 else 1827 { 1828 size_type __cap = __recommend(__reserve); 1829 __p = __alloc_traits::allocate(__alloc(), __cap+1); 1830 __set_long_pointer(__p); 1831 __set_long_cap(__cap+1); 1832 __set_long_size(__sz); 1833 } 1834 traits_type::copy(_VSTD::__to_address(__p), __s, __sz); 1835 traits_type::assign(__p[__sz], value_type()); 1836} 1837 1838template <class _CharT, class _Traits, class _Allocator> 1839void 1840basic_string<_CharT, _Traits, _Allocator>::__init(const value_type* __s, size_type __sz) 1841{ 1842 if (__sz > max_size()) 1843 this->__throw_length_error(); 1844 pointer __p; 1845 if (__sz < __min_cap) 1846 { 1847 __set_short_size(__sz); 1848 __p = __get_short_pointer(); 1849 } 1850 else 1851 { 1852 size_type __cap = __recommend(__sz); 1853 __p = __alloc_traits::allocate(__alloc(), __cap+1); 1854 __set_long_pointer(__p); 1855 __set_long_cap(__cap+1); 1856 __set_long_size(__sz); 1857 } 1858 traits_type::copy(_VSTD::__to_address(__p), __s, __sz); 1859 traits_type::assign(__p[__sz], value_type()); 1860} 1861 1862template <class _CharT, class _Traits, class _Allocator> 1863template <class> 1864basic_string<_CharT, _Traits, _Allocator>::basic_string(const _CharT* __s, const _Allocator& __a) 1865 : __r_(__default_init_tag(), __a) 1866{ 1867 _LIBCPP_ASSERT(__s != nullptr, "basic_string(const char*, allocator) detected nullptr"); 1868 __init(__s, traits_type::length(__s)); 1869#if _LIBCPP_DEBUG_LEVEL == 2 1870 __get_db()->__insert_c(this); 1871#endif 1872} 1873 1874template <class _CharT, class _Traits, class _Allocator> 1875inline 1876basic_string<_CharT, _Traits, _Allocator>::basic_string(const _CharT* __s, size_type __n) 1877 : __r_(__default_init_tag(), __default_init_tag()) 1878{ 1879 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "basic_string(const char*, n) detected nullptr"); 1880 __init(__s, __n); 1881#if _LIBCPP_DEBUG_LEVEL == 2 1882 __get_db()->__insert_c(this); 1883#endif 1884} 1885 1886template <class _CharT, class _Traits, class _Allocator> 1887inline 1888basic_string<_CharT, _Traits, _Allocator>::basic_string(const _CharT* __s, size_type __n, const _Allocator& __a) 1889 : __r_(__default_init_tag(), __a) 1890{ 1891 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "basic_string(const char*, n, allocator) detected nullptr"); 1892 __init(__s, __n); 1893#if _LIBCPP_DEBUG_LEVEL == 2 1894 __get_db()->__insert_c(this); 1895#endif 1896} 1897 1898template <class _CharT, class _Traits, class _Allocator> 1899basic_string<_CharT, _Traits, _Allocator>::basic_string(const basic_string& __str) 1900 : __r_(__default_init_tag(), __alloc_traits::select_on_container_copy_construction(__str.__alloc())) 1901{ 1902 if (!__str.__is_long()) 1903 __r_.first().__r = __str.__r_.first().__r; 1904 else 1905 __init_copy_ctor_external(_VSTD::__to_address(__str.__get_long_pointer()), 1906 __str.__get_long_size()); 1907 1908#if _LIBCPP_DEBUG_LEVEL == 2 1909 __get_db()->__insert_c(this); 1910#endif 1911} 1912 1913template <class _CharT, class _Traits, class _Allocator> 1914basic_string<_CharT, _Traits, _Allocator>::basic_string( 1915 const basic_string& __str, const allocator_type& __a) 1916 : __r_(__default_init_tag(), __a) 1917{ 1918 if (!__str.__is_long()) 1919 __r_.first().__r = __str.__r_.first().__r; 1920 else 1921 __init_copy_ctor_external(_VSTD::__to_address(__str.__get_long_pointer()), 1922 __str.__get_long_size()); 1923#if _LIBCPP_DEBUG_LEVEL == 2 1924 __get_db()->__insert_c(this); 1925#endif 1926} 1927 1928template <class _CharT, class _Traits, class _Allocator> 1929void basic_string<_CharT, _Traits, _Allocator>::__init_copy_ctor_external( 1930 const value_type* __s, size_type __sz) { 1931 pointer __p; 1932 if (__sz < __min_cap) { 1933 __p = __get_short_pointer(); 1934 __set_short_size(__sz); 1935 } else { 1936 if (__sz > max_size()) 1937 this->__throw_length_error(); 1938 size_t __cap = __recommend(__sz); 1939 __p = __alloc_traits::allocate(__alloc(), __cap + 1); 1940 __set_long_pointer(__p); 1941 __set_long_cap(__cap + 1); 1942 __set_long_size(__sz); 1943 } 1944 traits_type::copy(_VSTD::__to_address(__p), __s, __sz + 1); 1945} 1946 1947#ifndef _LIBCPP_CXX03_LANG 1948 1949template <class _CharT, class _Traits, class _Allocator> 1950inline 1951basic_string<_CharT, _Traits, _Allocator>::basic_string(basic_string&& __str) 1952#if _LIBCPP_STD_VER <= 14 1953 _NOEXCEPT_(is_nothrow_move_constructible<allocator_type>::value) 1954#else 1955 _NOEXCEPT 1956#endif 1957 : __r_(_VSTD::move(__str.__r_)) 1958{ 1959 __str.__zero(); 1960#if _LIBCPP_DEBUG_LEVEL == 2 1961 __get_db()->__insert_c(this); 1962 if (__is_long()) 1963 __get_db()->swap(this, &__str); 1964#endif 1965} 1966 1967template <class _CharT, class _Traits, class _Allocator> 1968inline 1969basic_string<_CharT, _Traits, _Allocator>::basic_string(basic_string&& __str, const allocator_type& __a) 1970 : __r_(__default_init_tag(), __a) 1971{ 1972 if (__str.__is_long() && __a != __str.__alloc()) // copy, not move 1973 __init(_VSTD::__to_address(__str.__get_long_pointer()), __str.__get_long_size()); 1974 else 1975 { 1976 __r_.first().__r = __str.__r_.first().__r; 1977 __str.__zero(); 1978 } 1979#if _LIBCPP_DEBUG_LEVEL == 2 1980 __get_db()->__insert_c(this); 1981 if (__is_long()) 1982 __get_db()->swap(this, &__str); 1983#endif 1984} 1985 1986#endif // _LIBCPP_CXX03_LANG 1987 1988template <class _CharT, class _Traits, class _Allocator> 1989void 1990basic_string<_CharT, _Traits, _Allocator>::__init(size_type __n, value_type __c) 1991{ 1992 if (__n > max_size()) 1993 this->__throw_length_error(); 1994 pointer __p; 1995 if (__n < __min_cap) 1996 { 1997 __set_short_size(__n); 1998 __p = __get_short_pointer(); 1999 } 2000 else 2001 { 2002 size_type __cap = __recommend(__n); 2003 __p = __alloc_traits::allocate(__alloc(), __cap+1); 2004 __set_long_pointer(__p); 2005 __set_long_cap(__cap+1); 2006 __set_long_size(__n); 2007 } 2008 traits_type::assign(_VSTD::__to_address(__p), __n, __c); 2009 traits_type::assign(__p[__n], value_type()); 2010} 2011 2012template <class _CharT, class _Traits, class _Allocator> 2013inline 2014basic_string<_CharT, _Traits, _Allocator>::basic_string(size_type __n, _CharT __c) 2015 : __r_(__default_init_tag(), __default_init_tag()) 2016{ 2017 __init(__n, __c); 2018#if _LIBCPP_DEBUG_LEVEL == 2 2019 __get_db()->__insert_c(this); 2020#endif 2021} 2022 2023template <class _CharT, class _Traits, class _Allocator> 2024template <class> 2025basic_string<_CharT, _Traits, _Allocator>::basic_string(size_type __n, _CharT __c, const _Allocator& __a) 2026 : __r_(__default_init_tag(), __a) 2027{ 2028 __init(__n, __c); 2029#if _LIBCPP_DEBUG_LEVEL == 2 2030 __get_db()->__insert_c(this); 2031#endif 2032} 2033 2034template <class _CharT, class _Traits, class _Allocator> 2035basic_string<_CharT, _Traits, _Allocator>::basic_string(const basic_string& __str, 2036 size_type __pos, size_type __n, 2037 const _Allocator& __a) 2038 : __r_(__default_init_tag(), __a) 2039{ 2040 size_type __str_sz = __str.size(); 2041 if (__pos > __str_sz) 2042 this->__throw_out_of_range(); 2043 __init(__str.data() + __pos, _VSTD::min(__n, __str_sz - __pos)); 2044#if _LIBCPP_DEBUG_LEVEL == 2 2045 __get_db()->__insert_c(this); 2046#endif 2047} 2048 2049template <class _CharT, class _Traits, class _Allocator> 2050inline 2051basic_string<_CharT, _Traits, _Allocator>::basic_string(const basic_string& __str, size_type __pos, 2052 const _Allocator& __a) 2053 : __r_(__default_init_tag(), __a) 2054{ 2055 size_type __str_sz = __str.size(); 2056 if (__pos > __str_sz) 2057 this->__throw_out_of_range(); 2058 __init(__str.data() + __pos, __str_sz - __pos); 2059#if _LIBCPP_DEBUG_LEVEL == 2 2060 __get_db()->__insert_c(this); 2061#endif 2062} 2063 2064template <class _CharT, class _Traits, class _Allocator> 2065template <class _Tp, class> 2066basic_string<_CharT, _Traits, _Allocator>::basic_string( 2067 const _Tp& __t, size_type __pos, size_type __n, const allocator_type& __a) 2068 : __r_(__default_init_tag(), __a) 2069{ 2070 __self_view __sv0 = __t; 2071 __self_view __sv = __sv0.substr(__pos, __n); 2072 __init(__sv.data(), __sv.size()); 2073#if _LIBCPP_DEBUG_LEVEL == 2 2074 __get_db()->__insert_c(this); 2075#endif 2076} 2077 2078template <class _CharT, class _Traits, class _Allocator> 2079template <class _Tp, class> 2080basic_string<_CharT, _Traits, _Allocator>::basic_string(const _Tp & __t) 2081 : __r_(__default_init_tag(), __default_init_tag()) 2082{ 2083 __self_view __sv = __t; 2084 __init(__sv.data(), __sv.size()); 2085#if _LIBCPP_DEBUG_LEVEL == 2 2086 __get_db()->__insert_c(this); 2087#endif 2088} 2089 2090template <class _CharT, class _Traits, class _Allocator> 2091template <class _Tp, class> 2092basic_string<_CharT, _Traits, _Allocator>::basic_string(const _Tp & __t, const _Allocator& __a) 2093 : __r_(__default_init_tag(), __a) 2094{ 2095 __self_view __sv = __t; 2096 __init(__sv.data(), __sv.size()); 2097#if _LIBCPP_DEBUG_LEVEL == 2 2098 __get_db()->__insert_c(this); 2099#endif 2100} 2101 2102template <class _CharT, class _Traits, class _Allocator> 2103template <class _InputIterator> 2104_EnableIf 2105< 2106 __is_exactly_cpp17_input_iterator<_InputIterator>::value 2107> 2108basic_string<_CharT, _Traits, _Allocator>::__init(_InputIterator __first, _InputIterator __last) 2109{ 2110 __zero(); 2111#ifndef _LIBCPP_NO_EXCEPTIONS 2112 try 2113 { 2114#endif // _LIBCPP_NO_EXCEPTIONS 2115 for (; __first != __last; ++__first) 2116 push_back(*__first); 2117#ifndef _LIBCPP_NO_EXCEPTIONS 2118 } 2119 catch (...) 2120 { 2121 if (__is_long()) 2122 __alloc_traits::deallocate(__alloc(), __get_long_pointer(), __get_long_cap()); 2123 throw; 2124 } 2125#endif // _LIBCPP_NO_EXCEPTIONS 2126} 2127 2128template <class _CharT, class _Traits, class _Allocator> 2129template <class _ForwardIterator> 2130_EnableIf 2131< 2132 __is_cpp17_forward_iterator<_ForwardIterator>::value 2133> 2134basic_string<_CharT, _Traits, _Allocator>::__init(_ForwardIterator __first, _ForwardIterator __last) 2135{ 2136 size_type __sz = static_cast<size_type>(_VSTD::distance(__first, __last)); 2137 if (__sz > max_size()) 2138 this->__throw_length_error(); 2139 pointer __p; 2140 if (__sz < __min_cap) 2141 { 2142 __set_short_size(__sz); 2143 __p = __get_short_pointer(); 2144 } 2145 else 2146 { 2147 size_type __cap = __recommend(__sz); 2148 __p = __alloc_traits::allocate(__alloc(), __cap+1); 2149 __set_long_pointer(__p); 2150 __set_long_cap(__cap+1); 2151 __set_long_size(__sz); 2152 } 2153 for (; __first != __last; ++__first, (void) ++__p) 2154 traits_type::assign(*__p, *__first); 2155 traits_type::assign(*__p, value_type()); 2156} 2157 2158template <class _CharT, class _Traits, class _Allocator> 2159template<class _InputIterator, class> 2160inline 2161basic_string<_CharT, _Traits, _Allocator>::basic_string(_InputIterator __first, _InputIterator __last) 2162 : __r_(__default_init_tag(), __default_init_tag()) 2163{ 2164 __init(__first, __last); 2165#if _LIBCPP_DEBUG_LEVEL == 2 2166 __get_db()->__insert_c(this); 2167#endif 2168} 2169 2170template <class _CharT, class _Traits, class _Allocator> 2171template<class _InputIterator, class> 2172inline 2173basic_string<_CharT, _Traits, _Allocator>::basic_string(_InputIterator __first, _InputIterator __last, 2174 const allocator_type& __a) 2175 : __r_(__default_init_tag(), __a) 2176{ 2177 __init(__first, __last); 2178#if _LIBCPP_DEBUG_LEVEL == 2 2179 __get_db()->__insert_c(this); 2180#endif 2181} 2182 2183#ifndef _LIBCPP_CXX03_LANG 2184 2185template <class _CharT, class _Traits, class _Allocator> 2186inline 2187basic_string<_CharT, _Traits, _Allocator>::basic_string( 2188 initializer_list<_CharT> __il) 2189 : __r_(__default_init_tag(), __default_init_tag()) 2190{ 2191 __init(__il.begin(), __il.end()); 2192#if _LIBCPP_DEBUG_LEVEL == 2 2193 __get_db()->__insert_c(this); 2194#endif 2195} 2196 2197template <class _CharT, class _Traits, class _Allocator> 2198inline 2199 2200basic_string<_CharT, _Traits, _Allocator>::basic_string( 2201 initializer_list<_CharT> __il, const _Allocator& __a) 2202 : __r_(__default_init_tag(), __a) 2203{ 2204 __init(__il.begin(), __il.end()); 2205#if _LIBCPP_DEBUG_LEVEL == 2 2206 __get_db()->__insert_c(this); 2207#endif 2208} 2209 2210#endif // _LIBCPP_CXX03_LANG 2211 2212template <class _CharT, class _Traits, class _Allocator> 2213basic_string<_CharT, _Traits, _Allocator>::~basic_string() 2214{ 2215#if _LIBCPP_DEBUG_LEVEL == 2 2216 __get_db()->__erase_c(this); 2217#endif 2218 if (__is_long()) 2219 __alloc_traits::deallocate(__alloc(), __get_long_pointer(), __get_long_cap()); 2220} 2221 2222template <class _CharT, class _Traits, class _Allocator> 2223void 2224basic_string<_CharT, _Traits, _Allocator>::__grow_by_and_replace 2225 (size_type __old_cap, size_type __delta_cap, size_type __old_sz, 2226 size_type __n_copy, size_type __n_del, size_type __n_add, const value_type* __p_new_stuff) 2227{ 2228 size_type __ms = max_size(); 2229 if (__delta_cap > __ms - __old_cap - 1) 2230 this->__throw_length_error(); 2231 pointer __old_p = __get_pointer(); 2232 size_type __cap = __old_cap < __ms / 2 - __alignment ? 2233 __recommend(_VSTD::max(__old_cap + __delta_cap, 2 * __old_cap)) : 2234 __ms - 1; 2235 pointer __p = __alloc_traits::allocate(__alloc(), __cap+1); 2236 __invalidate_all_iterators(); 2237 if (__n_copy != 0) 2238 traits_type::copy(_VSTD::__to_address(__p), 2239 _VSTD::__to_address(__old_p), __n_copy); 2240 if (__n_add != 0) 2241 traits_type::copy(_VSTD::__to_address(__p) + __n_copy, __p_new_stuff, __n_add); 2242 size_type __sec_cp_sz = __old_sz - __n_del - __n_copy; 2243 if (__sec_cp_sz != 0) 2244 traits_type::copy(_VSTD::__to_address(__p) + __n_copy + __n_add, 2245 _VSTD::__to_address(__old_p) + __n_copy + __n_del, __sec_cp_sz); 2246 if (__old_cap+1 != __min_cap) 2247 __alloc_traits::deallocate(__alloc(), __old_p, __old_cap+1); 2248 __set_long_pointer(__p); 2249 __set_long_cap(__cap+1); 2250 __old_sz = __n_copy + __n_add + __sec_cp_sz; 2251 __set_long_size(__old_sz); 2252 traits_type::assign(__p[__old_sz], value_type()); 2253} 2254 2255template <class _CharT, class _Traits, class _Allocator> 2256void 2257basic_string<_CharT, _Traits, _Allocator>::__grow_by(size_type __old_cap, size_type __delta_cap, size_type __old_sz, 2258 size_type __n_copy, size_type __n_del, size_type __n_add) 2259{ 2260 size_type __ms = max_size(); 2261 if (__delta_cap > __ms - __old_cap) 2262 this->__throw_length_error(); 2263 pointer __old_p = __get_pointer(); 2264 size_type __cap = __old_cap < __ms / 2 - __alignment ? 2265 __recommend(_VSTD::max(__old_cap + __delta_cap, 2 * __old_cap)) : 2266 __ms - 1; 2267 pointer __p = __alloc_traits::allocate(__alloc(), __cap+1); 2268 __invalidate_all_iterators(); 2269 if (__n_copy != 0) 2270 traits_type::copy(_VSTD::__to_address(__p), 2271 _VSTD::__to_address(__old_p), __n_copy); 2272 size_type __sec_cp_sz = __old_sz - __n_del - __n_copy; 2273 if (__sec_cp_sz != 0) 2274 traits_type::copy(_VSTD::__to_address(__p) + __n_copy + __n_add, 2275 _VSTD::__to_address(__old_p) + __n_copy + __n_del, 2276 __sec_cp_sz); 2277 if (__old_cap+1 != __min_cap) 2278 __alloc_traits::deallocate(__alloc(), __old_p, __old_cap+1); 2279 __set_long_pointer(__p); 2280 __set_long_cap(__cap+1); 2281} 2282 2283// assign 2284 2285template <class _CharT, class _Traits, class _Allocator> 2286template <bool __is_short> 2287basic_string<_CharT, _Traits, _Allocator>& 2288basic_string<_CharT, _Traits, _Allocator>::__assign_no_alias( 2289 const value_type* __s, size_type __n) { 2290 size_type __cap = __is_short ? __min_cap : __get_long_cap(); 2291 if (__n < __cap) { 2292 pointer __p = __is_short ? __get_short_pointer() : __get_long_pointer(); 2293 __is_short ? __set_short_size(__n) : __set_long_size(__n); 2294 traits_type::copy(_VSTD::__to_address(__p), __s, __n); 2295 traits_type::assign(__p[__n], value_type()); 2296 __invalidate_iterators_past(__n); 2297 } else { 2298 size_type __sz = __is_short ? __get_short_size() : __get_long_size(); 2299 __grow_by_and_replace(__cap - 1, __n - __cap + 1, __sz, 0, __sz, __n, __s); 2300 } 2301 return *this; 2302} 2303 2304template <class _CharT, class _Traits, class _Allocator> 2305basic_string<_CharT, _Traits, _Allocator>& 2306basic_string<_CharT, _Traits, _Allocator>::__assign_external( 2307 const value_type* __s, size_type __n) { 2308 size_type __cap = capacity(); 2309 if (__cap >= __n) { 2310 value_type* __p = _VSTD::__to_address(__get_pointer()); 2311 traits_type::move(__p, __s, __n); 2312 traits_type::assign(__p[__n], value_type()); 2313 __set_size(__n); 2314 __invalidate_iterators_past(__n); 2315 } else { 2316 size_type __sz = size(); 2317 __grow_by_and_replace(__cap, __n - __cap, __sz, 0, __sz, __n, __s); 2318 } 2319 return *this; 2320} 2321 2322template <class _CharT, class _Traits, class _Allocator> 2323basic_string<_CharT, _Traits, _Allocator>& 2324basic_string<_CharT, _Traits, _Allocator>::assign(const value_type* __s, size_type __n) 2325{ 2326 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::assign received nullptr"); 2327 return (_LIBCPP_BUILTIN_CONSTANT_P(__n) && __n < __min_cap) 2328 ? __assign_short(__s, __n) 2329 : __assign_external(__s, __n); 2330} 2331 2332template <class _CharT, class _Traits, class _Allocator> 2333basic_string<_CharT, _Traits, _Allocator>& 2334basic_string<_CharT, _Traits, _Allocator>::assign(size_type __n, value_type __c) 2335{ 2336 size_type __cap = capacity(); 2337 if (__cap < __n) 2338 { 2339 size_type __sz = size(); 2340 __grow_by(__cap, __n - __cap, __sz, 0, __sz); 2341 } 2342 else 2343 __invalidate_iterators_past(__n); 2344 value_type* __p = _VSTD::__to_address(__get_pointer()); 2345 traits_type::assign(__p, __n, __c); 2346 traits_type::assign(__p[__n], value_type()); 2347 __set_size(__n); 2348 return *this; 2349} 2350 2351template <class _CharT, class _Traits, class _Allocator> 2352basic_string<_CharT, _Traits, _Allocator>& 2353basic_string<_CharT, _Traits, _Allocator>::operator=(value_type __c) 2354{ 2355 pointer __p; 2356 if (__is_long()) 2357 { 2358 __p = __get_long_pointer(); 2359 __set_long_size(1); 2360 } 2361 else 2362 { 2363 __p = __get_short_pointer(); 2364 __set_short_size(1); 2365 } 2366 traits_type::assign(*__p, __c); 2367 traits_type::assign(*++__p, value_type()); 2368 __invalidate_iterators_past(1); 2369 return *this; 2370} 2371 2372template <class _CharT, class _Traits, class _Allocator> 2373basic_string<_CharT, _Traits, _Allocator>& 2374basic_string<_CharT, _Traits, _Allocator>::operator=(const basic_string& __str) 2375{ 2376 if (this != &__str) { 2377 __copy_assign_alloc(__str); 2378 if (!__is_long()) { 2379 if (!__str.__is_long()) { 2380 __r_.first().__r = __str.__r_.first().__r; 2381 } else { 2382 return __assign_no_alias<true>(__str.data(), __str.size()); 2383 } 2384 } else { 2385 return __assign_no_alias<false>(__str.data(), __str.size()); 2386 } 2387 } 2388 return *this; 2389} 2390 2391#ifndef _LIBCPP_CXX03_LANG 2392 2393template <class _CharT, class _Traits, class _Allocator> 2394inline 2395void 2396basic_string<_CharT, _Traits, _Allocator>::__move_assign(basic_string& __str, false_type) 2397 _NOEXCEPT_(__alloc_traits::is_always_equal::value) 2398{ 2399 if (__alloc() != __str.__alloc()) 2400 assign(__str); 2401 else 2402 __move_assign(__str, true_type()); 2403} 2404 2405template <class _CharT, class _Traits, class _Allocator> 2406inline 2407void 2408basic_string<_CharT, _Traits, _Allocator>::__move_assign(basic_string& __str, true_type) 2409#if _LIBCPP_STD_VER > 14 2410 _NOEXCEPT 2411#else 2412 _NOEXCEPT_(is_nothrow_move_assignable<allocator_type>::value) 2413#endif 2414{ 2415 if (__is_long()) { 2416 __alloc_traits::deallocate(__alloc(), __get_long_pointer(), 2417 __get_long_cap()); 2418#if _LIBCPP_STD_VER <= 14 2419 if (!is_nothrow_move_assignable<allocator_type>::value) { 2420 __set_short_size(0); 2421 traits_type::assign(__get_short_pointer()[0], value_type()); 2422 } 2423#endif 2424 } 2425 __move_assign_alloc(__str); 2426 __r_.first() = __str.__r_.first(); 2427 __str.__set_short_size(0); 2428 traits_type::assign(__str.__get_short_pointer()[0], value_type()); 2429} 2430 2431template <class _CharT, class _Traits, class _Allocator> 2432inline 2433basic_string<_CharT, _Traits, _Allocator>& 2434basic_string<_CharT, _Traits, _Allocator>::operator=(basic_string&& __str) 2435 _NOEXCEPT_((__noexcept_move_assign_container<_Allocator, __alloc_traits>::value)) 2436{ 2437 __move_assign(__str, integral_constant<bool, 2438 __alloc_traits::propagate_on_container_move_assignment::value>()); 2439 return *this; 2440} 2441 2442#endif 2443 2444template <class _CharT, class _Traits, class _Allocator> 2445template<class _InputIterator> 2446_EnableIf 2447< 2448 __is_exactly_cpp17_input_iterator <_InputIterator>::value 2449 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value, 2450 basic_string<_CharT, _Traits, _Allocator>& 2451> 2452basic_string<_CharT, _Traits, _Allocator>::assign(_InputIterator __first, _InputIterator __last) 2453{ 2454 const basic_string __temp(__first, __last, __alloc()); 2455 assign(__temp.data(), __temp.size()); 2456 return *this; 2457} 2458 2459template <class _CharT, class _Traits, class _Allocator> 2460template<class _ForwardIterator> 2461_EnableIf 2462< 2463 __is_cpp17_forward_iterator<_ForwardIterator>::value 2464 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value, 2465 basic_string<_CharT, _Traits, _Allocator>& 2466> 2467basic_string<_CharT, _Traits, _Allocator>::assign(_ForwardIterator __first, _ForwardIterator __last) 2468{ 2469 size_type __n = static_cast<size_type>(_VSTD::distance(__first, __last)); 2470 size_type __cap = capacity(); 2471 if (__cap < __n) 2472 { 2473 size_type __sz = size(); 2474 __grow_by(__cap, __n - __cap, __sz, 0, __sz); 2475 } 2476 else 2477 __invalidate_iterators_past(__n); 2478 pointer __p = __get_pointer(); 2479 for (; __first != __last; ++__first, ++__p) 2480 traits_type::assign(*__p, *__first); 2481 traits_type::assign(*__p, value_type()); 2482 __set_size(__n); 2483 return *this; 2484} 2485 2486template <class _CharT, class _Traits, class _Allocator> 2487basic_string<_CharT, _Traits, _Allocator>& 2488basic_string<_CharT, _Traits, _Allocator>::assign(const basic_string& __str, size_type __pos, size_type __n) 2489{ 2490 size_type __sz = __str.size(); 2491 if (__pos > __sz) 2492 this->__throw_out_of_range(); 2493 return assign(__str.data() + __pos, _VSTD::min(__n, __sz - __pos)); 2494} 2495 2496template <class _CharT, class _Traits, class _Allocator> 2497template <class _Tp> 2498_EnableIf 2499< 2500 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value 2501 && !__is_same_uncvref<_Tp, basic_string<_CharT, _Traits, _Allocator> >::value, 2502 basic_string<_CharT, _Traits, _Allocator>& 2503> 2504basic_string<_CharT, _Traits, _Allocator>::assign(const _Tp & __t, size_type __pos, size_type __n) 2505{ 2506 __self_view __sv = __t; 2507 size_type __sz = __sv.size(); 2508 if (__pos > __sz) 2509 this->__throw_out_of_range(); 2510 return assign(__sv.data() + __pos, _VSTD::min(__n, __sz - __pos)); 2511} 2512 2513 2514template <class _CharT, class _Traits, class _Allocator> 2515basic_string<_CharT, _Traits, _Allocator>& 2516basic_string<_CharT, _Traits, _Allocator>::__assign_external(const value_type* __s) { 2517 return __assign_external(__s, traits_type::length(__s)); 2518} 2519 2520template <class _CharT, class _Traits, class _Allocator> 2521basic_string<_CharT, _Traits, _Allocator>& 2522basic_string<_CharT, _Traits, _Allocator>::assign(const value_type* __s) 2523{ 2524 _LIBCPP_ASSERT(__s != nullptr, "string::assign received nullptr"); 2525 return _LIBCPP_BUILTIN_CONSTANT_P(*__s) 2526 ? (traits_type::length(__s) < __min_cap 2527 ? __assign_short(__s, traits_type::length(__s)) 2528 : __assign_external(__s, traits_type::length(__s))) 2529 : __assign_external(__s); 2530} 2531// append 2532 2533template <class _CharT, class _Traits, class _Allocator> 2534basic_string<_CharT, _Traits, _Allocator>& 2535basic_string<_CharT, _Traits, _Allocator>::append(const value_type* __s, size_type __n) 2536{ 2537 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::append received nullptr"); 2538 size_type __cap = capacity(); 2539 size_type __sz = size(); 2540 if (__cap - __sz >= __n) 2541 { 2542 if (__n) 2543 { 2544 value_type* __p = _VSTD::__to_address(__get_pointer()); 2545 traits_type::copy(__p + __sz, __s, __n); 2546 __sz += __n; 2547 __set_size(__sz); 2548 traits_type::assign(__p[__sz], value_type()); 2549 } 2550 } 2551 else 2552 __grow_by_and_replace(__cap, __sz + __n - __cap, __sz, __sz, 0, __n, __s); 2553 return *this; 2554} 2555 2556template <class _CharT, class _Traits, class _Allocator> 2557basic_string<_CharT, _Traits, _Allocator>& 2558basic_string<_CharT, _Traits, _Allocator>::append(size_type __n, value_type __c) 2559{ 2560 if (__n) 2561 { 2562 size_type __cap = capacity(); 2563 size_type __sz = size(); 2564 if (__cap - __sz < __n) 2565 __grow_by(__cap, __sz + __n - __cap, __sz, __sz, 0); 2566 pointer __p = __get_pointer(); 2567 traits_type::assign(_VSTD::__to_address(__p) + __sz, __n, __c); 2568 __sz += __n; 2569 __set_size(__sz); 2570 traits_type::assign(__p[__sz], value_type()); 2571 } 2572 return *this; 2573} 2574 2575template <class _CharT, class _Traits, class _Allocator> 2576inline void 2577basic_string<_CharT, _Traits, _Allocator>::__append_default_init(size_type __n) 2578{ 2579 if (__n) 2580 { 2581 size_type __cap = capacity(); 2582 size_type __sz = size(); 2583 if (__cap - __sz < __n) 2584 __grow_by(__cap, __sz + __n - __cap, __sz, __sz, 0); 2585 pointer __p = __get_pointer(); 2586 __sz += __n; 2587 __set_size(__sz); 2588 traits_type::assign(__p[__sz], value_type()); 2589 } 2590} 2591 2592template <class _CharT, class _Traits, class _Allocator> 2593void 2594basic_string<_CharT, _Traits, _Allocator>::push_back(value_type __c) 2595{ 2596 bool __is_short = !__is_long(); 2597 size_type __cap; 2598 size_type __sz; 2599 if (__is_short) 2600 { 2601 __cap = __min_cap - 1; 2602 __sz = __get_short_size(); 2603 } 2604 else 2605 { 2606 __cap = __get_long_cap() - 1; 2607 __sz = __get_long_size(); 2608 } 2609 if (__sz == __cap) 2610 { 2611 __grow_by(__cap, 1, __sz, __sz, 0); 2612 __is_short = !__is_long(); 2613 } 2614 pointer __p; 2615 if (__is_short) 2616 { 2617 __p = __get_short_pointer() + __sz; 2618 __set_short_size(__sz+1); 2619 } 2620 else 2621 { 2622 __p = __get_long_pointer() + __sz; 2623 __set_long_size(__sz+1); 2624 } 2625 traits_type::assign(*__p, __c); 2626 traits_type::assign(*++__p, value_type()); 2627} 2628 2629template <class _Tp> 2630bool __ptr_in_range (const _Tp* __p, const _Tp* __first, const _Tp* __last) 2631{ 2632 return __first <= __p && __p < __last; 2633} 2634 2635template <class _Tp1, class _Tp2> 2636bool __ptr_in_range (const _Tp1*, const _Tp2*, const _Tp2*) 2637{ 2638 return false; 2639} 2640 2641template <class _CharT, class _Traits, class _Allocator> 2642template<class _ForwardIterator> 2643basic_string<_CharT, _Traits, _Allocator>& 2644basic_string<_CharT, _Traits, _Allocator>::__append_forward_unsafe( 2645 _ForwardIterator __first, _ForwardIterator __last) 2646{ 2647 static_assert(__is_cpp17_forward_iterator<_ForwardIterator>::value, 2648 "function requires a ForwardIterator"); 2649 size_type __sz = size(); 2650 size_type __cap = capacity(); 2651 size_type __n = static_cast<size_type>(_VSTD::distance(__first, __last)); 2652 if (__n) 2653 { 2654 typedef typename iterator_traits<_ForwardIterator>::reference _CharRef; 2655 _CharRef __tmp_ref = *__first; 2656 if (__ptr_in_range(_VSTD::addressof(__tmp_ref), data(), data() + size())) 2657 { 2658 const basic_string __temp (__first, __last, __alloc()); 2659 append(__temp.data(), __temp.size()); 2660 } 2661 else 2662 { 2663 if (__cap - __sz < __n) 2664 __grow_by(__cap, __sz + __n - __cap, __sz, __sz, 0); 2665 pointer __p = __get_pointer() + __sz; 2666 for (; __first != __last; ++__p, ++__first) 2667 traits_type::assign(*__p, *__first); 2668 traits_type::assign(*__p, value_type()); 2669 __set_size(__sz + __n); 2670 } 2671 } 2672 return *this; 2673} 2674 2675template <class _CharT, class _Traits, class _Allocator> 2676inline 2677basic_string<_CharT, _Traits, _Allocator>& 2678basic_string<_CharT, _Traits, _Allocator>::append(const basic_string& __str) 2679{ 2680 return append(__str.data(), __str.size()); 2681} 2682 2683template <class _CharT, class _Traits, class _Allocator> 2684basic_string<_CharT, _Traits, _Allocator>& 2685basic_string<_CharT, _Traits, _Allocator>::append(const basic_string& __str, size_type __pos, size_type __n) 2686{ 2687 size_type __sz = __str.size(); 2688 if (__pos > __sz) 2689 this->__throw_out_of_range(); 2690 return append(__str.data() + __pos, _VSTD::min(__n, __sz - __pos)); 2691} 2692 2693template <class _CharT, class _Traits, class _Allocator> 2694template <class _Tp> 2695 _EnableIf 2696 < 2697 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string<_CharT, _Traits, _Allocator> >::value, 2698 basic_string<_CharT, _Traits, _Allocator>& 2699 > 2700basic_string<_CharT, _Traits, _Allocator>::append(const _Tp & __t, size_type __pos, size_type __n) 2701{ 2702 __self_view __sv = __t; 2703 size_type __sz = __sv.size(); 2704 if (__pos > __sz) 2705 this->__throw_out_of_range(); 2706 return append(__sv.data() + __pos, _VSTD::min(__n, __sz - __pos)); 2707} 2708 2709template <class _CharT, class _Traits, class _Allocator> 2710basic_string<_CharT, _Traits, _Allocator>& 2711basic_string<_CharT, _Traits, _Allocator>::append(const value_type* __s) 2712{ 2713 _LIBCPP_ASSERT(__s != nullptr, "string::append received nullptr"); 2714 return append(__s, traits_type::length(__s)); 2715} 2716 2717// insert 2718 2719template <class _CharT, class _Traits, class _Allocator> 2720basic_string<_CharT, _Traits, _Allocator>& 2721basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos, const value_type* __s, size_type __n) 2722{ 2723 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::insert received nullptr"); 2724 size_type __sz = size(); 2725 if (__pos > __sz) 2726 this->__throw_out_of_range(); 2727 size_type __cap = capacity(); 2728 if (__cap - __sz >= __n) 2729 { 2730 if (__n) 2731 { 2732 value_type* __p = _VSTD::__to_address(__get_pointer()); 2733 size_type __n_move = __sz - __pos; 2734 if (__n_move != 0) 2735 { 2736 if (__p + __pos <= __s && __s < __p + __sz) 2737 __s += __n; 2738 traits_type::move(__p + __pos + __n, __p + __pos, __n_move); 2739 } 2740 traits_type::move(__p + __pos, __s, __n); 2741 __sz += __n; 2742 __set_size(__sz); 2743 traits_type::assign(__p[__sz], value_type()); 2744 } 2745 } 2746 else 2747 __grow_by_and_replace(__cap, __sz + __n - __cap, __sz, __pos, 0, __n, __s); 2748 return *this; 2749} 2750 2751template <class _CharT, class _Traits, class _Allocator> 2752basic_string<_CharT, _Traits, _Allocator>& 2753basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos, size_type __n, value_type __c) 2754{ 2755 size_type __sz = size(); 2756 if (__pos > __sz) 2757 this->__throw_out_of_range(); 2758 if (__n) 2759 { 2760 size_type __cap = capacity(); 2761 value_type* __p; 2762 if (__cap - __sz >= __n) 2763 { 2764 __p = _VSTD::__to_address(__get_pointer()); 2765 size_type __n_move = __sz - __pos; 2766 if (__n_move != 0) 2767 traits_type::move(__p + __pos + __n, __p + __pos, __n_move); 2768 } 2769 else 2770 { 2771 __grow_by(__cap, __sz + __n - __cap, __sz, __pos, 0, __n); 2772 __p = _VSTD::__to_address(__get_long_pointer()); 2773 } 2774 traits_type::assign(__p + __pos, __n, __c); 2775 __sz += __n; 2776 __set_size(__sz); 2777 traits_type::assign(__p[__sz], value_type()); 2778 } 2779 return *this; 2780} 2781 2782template <class _CharT, class _Traits, class _Allocator> 2783template<class _InputIterator> 2784_EnableIf 2785< 2786 __is_exactly_cpp17_input_iterator<_InputIterator>::value 2787 || !__libcpp_string_gets_noexcept_iterator<_InputIterator>::value, 2788 typename basic_string<_CharT, _Traits, _Allocator>::iterator 2789> 2790basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, _InputIterator __first, _InputIterator __last) 2791{ 2792#if _LIBCPP_DEBUG_LEVEL == 2 2793 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this, 2794 "string::insert(iterator, range) called with an iterator not" 2795 " referring to this string"); 2796#endif 2797 const basic_string __temp(__first, __last, __alloc()); 2798 return insert(__pos, __temp.data(), __temp.data() + __temp.size()); 2799} 2800 2801template <class _CharT, class _Traits, class _Allocator> 2802template<class _ForwardIterator> 2803_EnableIf 2804< 2805 __is_cpp17_forward_iterator<_ForwardIterator>::value 2806 && __libcpp_string_gets_noexcept_iterator<_ForwardIterator>::value, 2807 typename basic_string<_CharT, _Traits, _Allocator>::iterator 2808> 2809basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, _ForwardIterator __first, _ForwardIterator __last) 2810{ 2811#if _LIBCPP_DEBUG_LEVEL == 2 2812 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this, 2813 "string::insert(iterator, range) called with an iterator not" 2814 " referring to this string"); 2815#endif 2816 size_type __ip = static_cast<size_type>(__pos - begin()); 2817 size_type __n = static_cast<size_type>(_VSTD::distance(__first, __last)); 2818 if (__n) 2819 { 2820 typedef typename iterator_traits<_ForwardIterator>::reference _CharRef; 2821 _CharRef __tmp_char = *__first; 2822 if (__ptr_in_range(_VSTD::addressof(__tmp_char), data(), data() + size())) 2823 { 2824 const basic_string __temp(__first, __last, __alloc()); 2825 return insert(__pos, __temp.data(), __temp.data() + __temp.size()); 2826 } 2827 2828 size_type __sz = size(); 2829 size_type __cap = capacity(); 2830 value_type* __p; 2831 if (__cap - __sz >= __n) 2832 { 2833 __p = _VSTD::__to_address(__get_pointer()); 2834 size_type __n_move = __sz - __ip; 2835 if (__n_move != 0) 2836 traits_type::move(__p + __ip + __n, __p + __ip, __n_move); 2837 } 2838 else 2839 { 2840 __grow_by(__cap, __sz + __n - __cap, __sz, __ip, 0, __n); 2841 __p = _VSTD::__to_address(__get_long_pointer()); 2842 } 2843 __sz += __n; 2844 __set_size(__sz); 2845 traits_type::assign(__p[__sz], value_type()); 2846 for (__p += __ip; __first != __last; ++__p, ++__first) 2847 traits_type::assign(*__p, *__first); 2848 } 2849 return begin() + __ip; 2850} 2851 2852template <class _CharT, class _Traits, class _Allocator> 2853inline 2854basic_string<_CharT, _Traits, _Allocator>& 2855basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos1, const basic_string& __str) 2856{ 2857 return insert(__pos1, __str.data(), __str.size()); 2858} 2859 2860template <class _CharT, class _Traits, class _Allocator> 2861basic_string<_CharT, _Traits, _Allocator>& 2862basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos1, const basic_string& __str, 2863 size_type __pos2, size_type __n) 2864{ 2865 size_type __str_sz = __str.size(); 2866 if (__pos2 > __str_sz) 2867 this->__throw_out_of_range(); 2868 return insert(__pos1, __str.data() + __pos2, _VSTD::min(__n, __str_sz - __pos2)); 2869} 2870 2871template <class _CharT, class _Traits, class _Allocator> 2872template <class _Tp> 2873_EnableIf 2874< 2875 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string<_CharT, _Traits, _Allocator> >::value, 2876 basic_string<_CharT, _Traits, _Allocator>& 2877> 2878basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos1, const _Tp& __t, 2879 size_type __pos2, size_type __n) 2880{ 2881 __self_view __sv = __t; 2882 size_type __str_sz = __sv.size(); 2883 if (__pos2 > __str_sz) 2884 this->__throw_out_of_range(); 2885 return insert(__pos1, __sv.data() + __pos2, _VSTD::min(__n, __str_sz - __pos2)); 2886} 2887 2888template <class _CharT, class _Traits, class _Allocator> 2889basic_string<_CharT, _Traits, _Allocator>& 2890basic_string<_CharT, _Traits, _Allocator>::insert(size_type __pos, const value_type* __s) 2891{ 2892 _LIBCPP_ASSERT(__s != nullptr, "string::insert received nullptr"); 2893 return insert(__pos, __s, traits_type::length(__s)); 2894} 2895 2896template <class _CharT, class _Traits, class _Allocator> 2897typename basic_string<_CharT, _Traits, _Allocator>::iterator 2898basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, value_type __c) 2899{ 2900 size_type __ip = static_cast<size_type>(__pos - begin()); 2901 size_type __sz = size(); 2902 size_type __cap = capacity(); 2903 value_type* __p; 2904 if (__cap == __sz) 2905 { 2906 __grow_by(__cap, 1, __sz, __ip, 0, 1); 2907 __p = _VSTD::__to_address(__get_long_pointer()); 2908 } 2909 else 2910 { 2911 __p = _VSTD::__to_address(__get_pointer()); 2912 size_type __n_move = __sz - __ip; 2913 if (__n_move != 0) 2914 traits_type::move(__p + __ip + 1, __p + __ip, __n_move); 2915 } 2916 traits_type::assign(__p[__ip], __c); 2917 traits_type::assign(__p[++__sz], value_type()); 2918 __set_size(__sz); 2919 return begin() + static_cast<difference_type>(__ip); 2920} 2921 2922template <class _CharT, class _Traits, class _Allocator> 2923inline 2924typename basic_string<_CharT, _Traits, _Allocator>::iterator 2925basic_string<_CharT, _Traits, _Allocator>::insert(const_iterator __pos, size_type __n, value_type __c) 2926{ 2927#if _LIBCPP_DEBUG_LEVEL == 2 2928 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this, 2929 "string::insert(iterator, n, value) called with an iterator not" 2930 " referring to this string"); 2931#endif 2932 difference_type __p = __pos - begin(); 2933 insert(static_cast<size_type>(__p), __n, __c); 2934 return begin() + __p; 2935} 2936 2937// replace 2938 2939template <class _CharT, class _Traits, class _Allocator> 2940basic_string<_CharT, _Traits, _Allocator>& 2941basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos, size_type __n1, const value_type* __s, size_type __n2) 2942 _LIBCPP_DISABLE_UBSAN_UNSIGNED_INTEGER_CHECK 2943{ 2944 _LIBCPP_ASSERT(__n2 == 0 || __s != nullptr, "string::replace received nullptr"); 2945 size_type __sz = size(); 2946 if (__pos > __sz) 2947 this->__throw_out_of_range(); 2948 __n1 = _VSTD::min(__n1, __sz - __pos); 2949 size_type __cap = capacity(); 2950 if (__cap - __sz + __n1 >= __n2) 2951 { 2952 value_type* __p = _VSTD::__to_address(__get_pointer()); 2953 if (__n1 != __n2) 2954 { 2955 size_type __n_move = __sz - __pos - __n1; 2956 if (__n_move != 0) 2957 { 2958 if (__n1 > __n2) 2959 { 2960 traits_type::move(__p + __pos, __s, __n2); 2961 traits_type::move(__p + __pos + __n2, __p + __pos + __n1, __n_move); 2962 goto __finish; 2963 } 2964 if (__p + __pos < __s && __s < __p + __sz) 2965 { 2966 if (__p + __pos + __n1 <= __s) 2967 __s += __n2 - __n1; 2968 else // __p + __pos < __s < __p + __pos + __n1 2969 { 2970 traits_type::move(__p + __pos, __s, __n1); 2971 __pos += __n1; 2972 __s += __n2; 2973 __n2 -= __n1; 2974 __n1 = 0; 2975 } 2976 } 2977 traits_type::move(__p + __pos + __n2, __p + __pos + __n1, __n_move); 2978 } 2979 } 2980 traits_type::move(__p + __pos, __s, __n2); 2981__finish: 2982// __sz += __n2 - __n1; in this and the below function below can cause unsigned 2983// integer overflow, but this is a safe operation, so we disable the check. 2984 __sz += __n2 - __n1; 2985 __set_size(__sz); 2986 __invalidate_iterators_past(__sz); 2987 traits_type::assign(__p[__sz], value_type()); 2988 } 2989 else 2990 __grow_by_and_replace(__cap, __sz - __n1 + __n2 - __cap, __sz, __pos, __n1, __n2, __s); 2991 return *this; 2992} 2993 2994template <class _CharT, class _Traits, class _Allocator> 2995basic_string<_CharT, _Traits, _Allocator>& 2996basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos, size_type __n1, size_type __n2, value_type __c) 2997 _LIBCPP_DISABLE_UBSAN_UNSIGNED_INTEGER_CHECK 2998{ 2999 size_type __sz = size(); 3000 if (__pos > __sz) 3001 this->__throw_out_of_range(); 3002 __n1 = _VSTD::min(__n1, __sz - __pos); 3003 size_type __cap = capacity(); 3004 value_type* __p; 3005 if (__cap - __sz + __n1 >= __n2) 3006 { 3007 __p = _VSTD::__to_address(__get_pointer()); 3008 if (__n1 != __n2) 3009 { 3010 size_type __n_move = __sz - __pos - __n1; 3011 if (__n_move != 0) 3012 traits_type::move(__p + __pos + __n2, __p + __pos + __n1, __n_move); 3013 } 3014 } 3015 else 3016 { 3017 __grow_by(__cap, __sz - __n1 + __n2 - __cap, __sz, __pos, __n1, __n2); 3018 __p = _VSTD::__to_address(__get_long_pointer()); 3019 } 3020 traits_type::assign(__p + __pos, __n2, __c); 3021 __sz += __n2 - __n1; 3022 __set_size(__sz); 3023 __invalidate_iterators_past(__sz); 3024 traits_type::assign(__p[__sz], value_type()); 3025 return *this; 3026} 3027 3028template <class _CharT, class _Traits, class _Allocator> 3029template<class _InputIterator> 3030_EnableIf 3031< 3032 __is_cpp17_input_iterator<_InputIterator>::value, 3033 basic_string<_CharT, _Traits, _Allocator>& 3034> 3035basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, 3036 _InputIterator __j1, _InputIterator __j2) 3037{ 3038 const basic_string __temp(__j1, __j2, __alloc()); 3039 return this->replace(__i1, __i2, __temp); 3040} 3041 3042template <class _CharT, class _Traits, class _Allocator> 3043inline 3044basic_string<_CharT, _Traits, _Allocator>& 3045basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos1, size_type __n1, const basic_string& __str) 3046{ 3047 return replace(__pos1, __n1, __str.data(), __str.size()); 3048} 3049 3050template <class _CharT, class _Traits, class _Allocator> 3051basic_string<_CharT, _Traits, _Allocator>& 3052basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos1, size_type __n1, const basic_string& __str, 3053 size_type __pos2, size_type __n2) 3054{ 3055 size_type __str_sz = __str.size(); 3056 if (__pos2 > __str_sz) 3057 this->__throw_out_of_range(); 3058 return replace(__pos1, __n1, __str.data() + __pos2, _VSTD::min(__n2, __str_sz - __pos2)); 3059} 3060 3061template <class _CharT, class _Traits, class _Allocator> 3062template <class _Tp> 3063_EnableIf 3064< 3065 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value && !__is_same_uncvref<_Tp, basic_string<_CharT, _Traits, _Allocator> >::value, 3066 basic_string<_CharT, _Traits, _Allocator>& 3067> 3068basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos1, size_type __n1, const _Tp& __t, 3069 size_type __pos2, size_type __n2) 3070{ 3071 __self_view __sv = __t; 3072 size_type __str_sz = __sv.size(); 3073 if (__pos2 > __str_sz) 3074 this->__throw_out_of_range(); 3075 return replace(__pos1, __n1, __sv.data() + __pos2, _VSTD::min(__n2, __str_sz - __pos2)); 3076} 3077 3078template <class _CharT, class _Traits, class _Allocator> 3079basic_string<_CharT, _Traits, _Allocator>& 3080basic_string<_CharT, _Traits, _Allocator>::replace(size_type __pos, size_type __n1, const value_type* __s) 3081{ 3082 _LIBCPP_ASSERT(__s != nullptr, "string::replace received nullptr"); 3083 return replace(__pos, __n1, __s, traits_type::length(__s)); 3084} 3085 3086template <class _CharT, class _Traits, class _Allocator> 3087inline 3088basic_string<_CharT, _Traits, _Allocator>& 3089basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, const basic_string& __str) 3090{ 3091 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1), 3092 __str.data(), __str.size()); 3093} 3094 3095template <class _CharT, class _Traits, class _Allocator> 3096inline 3097basic_string<_CharT, _Traits, _Allocator>& 3098basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, const value_type* __s, size_type __n) 3099{ 3100 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1), __s, __n); 3101} 3102 3103template <class _CharT, class _Traits, class _Allocator> 3104inline 3105basic_string<_CharT, _Traits, _Allocator>& 3106basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, const value_type* __s) 3107{ 3108 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1), __s); 3109} 3110 3111template <class _CharT, class _Traits, class _Allocator> 3112inline 3113basic_string<_CharT, _Traits, _Allocator>& 3114basic_string<_CharT, _Traits, _Allocator>::replace(const_iterator __i1, const_iterator __i2, size_type __n, value_type __c) 3115{ 3116 return replace(static_cast<size_type>(__i1 - begin()), static_cast<size_type>(__i2 - __i1), __n, __c); 3117} 3118 3119// erase 3120 3121// 'externally instantiated' erase() implementation, called when __n != npos. 3122// Does not check __pos against size() 3123template <class _CharT, class _Traits, class _Allocator> 3124void 3125basic_string<_CharT, _Traits, _Allocator>::__erase_external_with_move( 3126 size_type __pos, size_type __n) 3127{ 3128 if (__n) 3129 { 3130 size_type __sz = size(); 3131 value_type* __p = _VSTD::__to_address(__get_pointer()); 3132 __n = _VSTD::min(__n, __sz - __pos); 3133 size_type __n_move = __sz - __pos - __n; 3134 if (__n_move != 0) 3135 traits_type::move(__p + __pos, __p + __pos + __n, __n_move); 3136 __sz -= __n; 3137 __set_size(__sz); 3138 __invalidate_iterators_past(__sz); 3139 traits_type::assign(__p[__sz], value_type()); 3140 } 3141} 3142 3143template <class _CharT, class _Traits, class _Allocator> 3144basic_string<_CharT, _Traits, _Allocator>& 3145basic_string<_CharT, _Traits, _Allocator>::erase(size_type __pos, 3146 size_type __n) { 3147 if (__pos > size()) this->__throw_out_of_range(); 3148 if (__n == npos) { 3149 __erase_to_end(__pos); 3150 } else { 3151 __erase_external_with_move(__pos, __n); 3152 } 3153 return *this; 3154} 3155 3156template <class _CharT, class _Traits, class _Allocator> 3157inline 3158typename basic_string<_CharT, _Traits, _Allocator>::iterator 3159basic_string<_CharT, _Traits, _Allocator>::erase(const_iterator __pos) 3160{ 3161#if _LIBCPP_DEBUG_LEVEL == 2 3162 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__pos) == this, 3163 "string::erase(iterator) called with an iterator not" 3164 " referring to this string"); 3165#endif 3166 _LIBCPP_ASSERT(__pos != end(), 3167 "string::erase(iterator) called with a non-dereferenceable iterator"); 3168 iterator __b = begin(); 3169 size_type __r = static_cast<size_type>(__pos - __b); 3170 erase(__r, 1); 3171 return __b + static_cast<difference_type>(__r); 3172} 3173 3174template <class _CharT, class _Traits, class _Allocator> 3175inline 3176typename basic_string<_CharT, _Traits, _Allocator>::iterator 3177basic_string<_CharT, _Traits, _Allocator>::erase(const_iterator __first, const_iterator __last) 3178{ 3179#if _LIBCPP_DEBUG_LEVEL == 2 3180 _LIBCPP_ASSERT(__get_const_db()->__find_c_from_i(&__first) == this, 3181 "string::erase(iterator, iterator) called with an iterator not" 3182 " referring to this string"); 3183#endif 3184 _LIBCPP_ASSERT(__first <= __last, "string::erase(first, last) called with invalid range"); 3185 iterator __b = begin(); 3186 size_type __r = static_cast<size_type>(__first - __b); 3187 erase(__r, static_cast<size_type>(__last - __first)); 3188 return __b + static_cast<difference_type>(__r); 3189} 3190 3191template <class _CharT, class _Traits, class _Allocator> 3192inline 3193void 3194basic_string<_CharT, _Traits, _Allocator>::pop_back() 3195{ 3196 _LIBCPP_ASSERT(!empty(), "string::pop_back(): string is already empty"); 3197 size_type __sz; 3198 if (__is_long()) 3199 { 3200 __sz = __get_long_size() - 1; 3201 __set_long_size(__sz); 3202 traits_type::assign(*(__get_long_pointer() + __sz), value_type()); 3203 } 3204 else 3205 { 3206 __sz = __get_short_size() - 1; 3207 __set_short_size(__sz); 3208 traits_type::assign(*(__get_short_pointer() + __sz), value_type()); 3209 } 3210 __invalidate_iterators_past(__sz); 3211} 3212 3213template <class _CharT, class _Traits, class _Allocator> 3214inline 3215void 3216basic_string<_CharT, _Traits, _Allocator>::clear() _NOEXCEPT 3217{ 3218 __invalidate_all_iterators(); 3219 if (__is_long()) 3220 { 3221 traits_type::assign(*__get_long_pointer(), value_type()); 3222 __set_long_size(0); 3223 } 3224 else 3225 { 3226 traits_type::assign(*__get_short_pointer(), value_type()); 3227 __set_short_size(0); 3228 } 3229} 3230 3231template <class _CharT, class _Traits, class _Allocator> 3232inline 3233void 3234basic_string<_CharT, _Traits, _Allocator>::__erase_to_end(size_type __pos) 3235{ 3236 if (__is_long()) 3237 { 3238 traits_type::assign(*(__get_long_pointer() + __pos), value_type()); 3239 __set_long_size(__pos); 3240 } 3241 else 3242 { 3243 traits_type::assign(*(__get_short_pointer() + __pos), value_type()); 3244 __set_short_size(__pos); 3245 } 3246 __invalidate_iterators_past(__pos); 3247} 3248 3249template <class _CharT, class _Traits, class _Allocator> 3250void 3251basic_string<_CharT, _Traits, _Allocator>::resize(size_type __n, value_type __c) 3252{ 3253 size_type __sz = size(); 3254 if (__n > __sz) 3255 append(__n - __sz, __c); 3256 else 3257 __erase_to_end(__n); 3258} 3259 3260template <class _CharT, class _Traits, class _Allocator> 3261inline void 3262basic_string<_CharT, _Traits, _Allocator>::__resize_default_init(size_type __n) 3263{ 3264 size_type __sz = size(); 3265 if (__n > __sz) { 3266 __append_default_init(__n - __sz); 3267 } else 3268 __erase_to_end(__n); 3269} 3270 3271template <class _CharT, class _Traits, class _Allocator> 3272inline 3273typename basic_string<_CharT, _Traits, _Allocator>::size_type 3274basic_string<_CharT, _Traits, _Allocator>::max_size() const _NOEXCEPT 3275{ 3276 size_type __m = __alloc_traits::max_size(__alloc()); 3277#ifdef _LIBCPP_BIG_ENDIAN 3278 return (__m <= ~__long_mask ? __m : __m/2) - __alignment; 3279#else 3280 return __m - __alignment; 3281#endif 3282} 3283 3284template <class _CharT, class _Traits, class _Allocator> 3285void 3286basic_string<_CharT, _Traits, _Allocator>::reserve(size_type __requested_capacity) 3287{ 3288 if (__requested_capacity > max_size()) 3289 this->__throw_length_error(); 3290 3291#if _LIBCPP_STD_VER > 17 3292 // Reserve never shrinks as of C++20. 3293 if (__requested_capacity <= capacity()) return; 3294#endif 3295 3296 size_type __target_capacity = _VSTD::max(__requested_capacity, size()); 3297 __target_capacity = __recommend(__target_capacity); 3298 if (__target_capacity == capacity()) return; 3299 3300 __shrink_or_extend(__target_capacity); 3301} 3302 3303template <class _CharT, class _Traits, class _Allocator> 3304void 3305basic_string<_CharT, _Traits, _Allocator>::shrink_to_fit() _NOEXCEPT 3306{ 3307 size_type __target_capacity = __recommend(size()); 3308 if (__target_capacity == capacity()) return; 3309 3310 __shrink_or_extend(__target_capacity); 3311} 3312 3313template <class _CharT, class _Traits, class _Allocator> 3314void 3315basic_string<_CharT, _Traits, _Allocator>::__shrink_or_extend(size_type __target_capacity) 3316{ 3317 size_type __cap = capacity(); 3318 size_type __sz = size(); 3319 3320 pointer __new_data, __p; 3321 bool __was_long, __now_long; 3322 if (__target_capacity == __min_cap - 1) 3323 { 3324 __was_long = true; 3325 __now_long = false; 3326 __new_data = __get_short_pointer(); 3327 __p = __get_long_pointer(); 3328 } 3329 else 3330 { 3331 if (__target_capacity > __cap) 3332 __new_data = __alloc_traits::allocate(__alloc(), __target_capacity+1); 3333 else 3334 { 3335 #ifndef _LIBCPP_NO_EXCEPTIONS 3336 try 3337 { 3338 #endif // _LIBCPP_NO_EXCEPTIONS 3339 __new_data = __alloc_traits::allocate(__alloc(), __target_capacity+1); 3340 #ifndef _LIBCPP_NO_EXCEPTIONS 3341 } 3342 catch (...) 3343 { 3344 return; 3345 } 3346 #else // _LIBCPP_NO_EXCEPTIONS 3347 if (__new_data == nullptr) 3348 return; 3349 #endif // _LIBCPP_NO_EXCEPTIONS 3350 } 3351 __now_long = true; 3352 __was_long = __is_long(); 3353 __p = __get_pointer(); 3354 } 3355 traits_type::copy(_VSTD::__to_address(__new_data), 3356 _VSTD::__to_address(__p), size()+1); 3357 if (__was_long) 3358 __alloc_traits::deallocate(__alloc(), __p, __cap+1); 3359 if (__now_long) 3360 { 3361 __set_long_cap(__target_capacity+1); 3362 __set_long_size(__sz); 3363 __set_long_pointer(__new_data); 3364 } 3365 else 3366 __set_short_size(__sz); 3367 __invalidate_all_iterators(); 3368} 3369 3370template <class _CharT, class _Traits, class _Allocator> 3371inline 3372typename basic_string<_CharT, _Traits, _Allocator>::const_reference 3373basic_string<_CharT, _Traits, _Allocator>::operator[](size_type __pos) const _NOEXCEPT 3374{ 3375 _LIBCPP_ASSERT(__pos <= size(), "string index out of bounds"); 3376 return *(data() + __pos); 3377} 3378 3379template <class _CharT, class _Traits, class _Allocator> 3380inline 3381typename basic_string<_CharT, _Traits, _Allocator>::reference 3382basic_string<_CharT, _Traits, _Allocator>::operator[](size_type __pos) _NOEXCEPT 3383{ 3384 _LIBCPP_ASSERT(__pos <= size(), "string index out of bounds"); 3385 return *(__get_pointer() + __pos); 3386} 3387 3388template <class _CharT, class _Traits, class _Allocator> 3389typename basic_string<_CharT, _Traits, _Allocator>::const_reference 3390basic_string<_CharT, _Traits, _Allocator>::at(size_type __n) const 3391{ 3392 if (__n >= size()) 3393 this->__throw_out_of_range(); 3394 return (*this)[__n]; 3395} 3396 3397template <class _CharT, class _Traits, class _Allocator> 3398typename basic_string<_CharT, _Traits, _Allocator>::reference 3399basic_string<_CharT, _Traits, _Allocator>::at(size_type __n) 3400{ 3401 if (__n >= size()) 3402 this->__throw_out_of_range(); 3403 return (*this)[__n]; 3404} 3405 3406template <class _CharT, class _Traits, class _Allocator> 3407inline 3408typename basic_string<_CharT, _Traits, _Allocator>::reference 3409basic_string<_CharT, _Traits, _Allocator>::front() _NOEXCEPT 3410{ 3411 _LIBCPP_ASSERT(!empty(), "string::front(): string is empty"); 3412 return *__get_pointer(); 3413} 3414 3415template <class _CharT, class _Traits, class _Allocator> 3416inline 3417typename basic_string<_CharT, _Traits, _Allocator>::const_reference 3418basic_string<_CharT, _Traits, _Allocator>::front() const _NOEXCEPT 3419{ 3420 _LIBCPP_ASSERT(!empty(), "string::front(): string is empty"); 3421 return *data(); 3422} 3423 3424template <class _CharT, class _Traits, class _Allocator> 3425inline 3426typename basic_string<_CharT, _Traits, _Allocator>::reference 3427basic_string<_CharT, _Traits, _Allocator>::back() _NOEXCEPT 3428{ 3429 _LIBCPP_ASSERT(!empty(), "string::back(): string is empty"); 3430 return *(__get_pointer() + size() - 1); 3431} 3432 3433template <class _CharT, class _Traits, class _Allocator> 3434inline 3435typename basic_string<_CharT, _Traits, _Allocator>::const_reference 3436basic_string<_CharT, _Traits, _Allocator>::back() const _NOEXCEPT 3437{ 3438 _LIBCPP_ASSERT(!empty(), "string::back(): string is empty"); 3439 return *(data() + size() - 1); 3440} 3441 3442template <class _CharT, class _Traits, class _Allocator> 3443typename basic_string<_CharT, _Traits, _Allocator>::size_type 3444basic_string<_CharT, _Traits, _Allocator>::copy(value_type* __s, size_type __n, size_type __pos) const 3445{ 3446 size_type __sz = size(); 3447 if (__pos > __sz) 3448 this->__throw_out_of_range(); 3449 size_type __rlen = _VSTD::min(__n, __sz - __pos); 3450 traits_type::copy(__s, data() + __pos, __rlen); 3451 return __rlen; 3452} 3453 3454template <class _CharT, class _Traits, class _Allocator> 3455inline 3456basic_string<_CharT, _Traits, _Allocator> 3457basic_string<_CharT, _Traits, _Allocator>::substr(size_type __pos, size_type __n) const 3458{ 3459 return basic_string(*this, __pos, __n, __alloc()); 3460} 3461 3462template <class _CharT, class _Traits, class _Allocator> 3463inline 3464void 3465basic_string<_CharT, _Traits, _Allocator>::swap(basic_string& __str) 3466#if _LIBCPP_STD_VER >= 14 3467 _NOEXCEPT 3468#else 3469 _NOEXCEPT_(!__alloc_traits::propagate_on_container_swap::value || 3470 __is_nothrow_swappable<allocator_type>::value) 3471#endif 3472{ 3473#if _LIBCPP_DEBUG_LEVEL == 2 3474 if (!__is_long()) 3475 __get_db()->__invalidate_all(this); 3476 if (!__str.__is_long()) 3477 __get_db()->__invalidate_all(&__str); 3478 __get_db()->swap(this, &__str); 3479#endif 3480 _LIBCPP_ASSERT( 3481 __alloc_traits::propagate_on_container_swap::value || 3482 __alloc_traits::is_always_equal::value || 3483 __alloc() == __str.__alloc(), "swapping non-equal allocators"); 3484 _VSTD::swap(__r_.first(), __str.__r_.first()); 3485 _VSTD::__swap_allocator(__alloc(), __str.__alloc()); 3486} 3487 3488// find 3489 3490template <class _Traits> 3491struct _LIBCPP_HIDDEN __traits_eq 3492{ 3493 typedef typename _Traits::char_type char_type; 3494 _LIBCPP_INLINE_VISIBILITY 3495 bool operator()(const char_type& __x, const char_type& __y) _NOEXCEPT 3496 {return _Traits::eq(__x, __y);} 3497}; 3498 3499template<class _CharT, class _Traits, class _Allocator> 3500typename basic_string<_CharT, _Traits, _Allocator>::size_type 3501basic_string<_CharT, _Traits, _Allocator>::find(const value_type* __s, 3502 size_type __pos, 3503 size_type __n) const _NOEXCEPT 3504{ 3505 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find(): received nullptr"); 3506 return __str_find<value_type, size_type, traits_type, npos> 3507 (data(), size(), __s, __pos, __n); 3508} 3509 3510template<class _CharT, class _Traits, class _Allocator> 3511inline 3512typename basic_string<_CharT, _Traits, _Allocator>::size_type 3513basic_string<_CharT, _Traits, _Allocator>::find(const basic_string& __str, 3514 size_type __pos) const _NOEXCEPT 3515{ 3516 return __str_find<value_type, size_type, traits_type, npos> 3517 (data(), size(), __str.data(), __pos, __str.size()); 3518} 3519 3520template<class _CharT, class _Traits, class _Allocator> 3521template <class _Tp> 3522_EnableIf 3523< 3524 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3525 typename basic_string<_CharT, _Traits, _Allocator>::size_type 3526> 3527basic_string<_CharT, _Traits, _Allocator>::find(const _Tp &__t, 3528 size_type __pos) const 3529{ 3530 __self_view __sv = __t; 3531 return __str_find<value_type, size_type, traits_type, npos> 3532 (data(), size(), __sv.data(), __pos, __sv.size()); 3533} 3534 3535template<class _CharT, class _Traits, class _Allocator> 3536inline 3537typename basic_string<_CharT, _Traits, _Allocator>::size_type 3538basic_string<_CharT, _Traits, _Allocator>::find(const value_type* __s, 3539 size_type __pos) const _NOEXCEPT 3540{ 3541 _LIBCPP_ASSERT(__s != nullptr, "string::find(): received nullptr"); 3542 return __str_find<value_type, size_type, traits_type, npos> 3543 (data(), size(), __s, __pos, traits_type::length(__s)); 3544} 3545 3546template<class _CharT, class _Traits, class _Allocator> 3547typename basic_string<_CharT, _Traits, _Allocator>::size_type 3548basic_string<_CharT, _Traits, _Allocator>::find(value_type __c, 3549 size_type __pos) const _NOEXCEPT 3550{ 3551 return __str_find<value_type, size_type, traits_type, npos> 3552 (data(), size(), __c, __pos); 3553} 3554 3555// rfind 3556 3557template<class _CharT, class _Traits, class _Allocator> 3558typename basic_string<_CharT, _Traits, _Allocator>::size_type 3559basic_string<_CharT, _Traits, _Allocator>::rfind(const value_type* __s, 3560 size_type __pos, 3561 size_type __n) const _NOEXCEPT 3562{ 3563 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::rfind(): received nullptr"); 3564 return __str_rfind<value_type, size_type, traits_type, npos> 3565 (data(), size(), __s, __pos, __n); 3566} 3567 3568template<class _CharT, class _Traits, class _Allocator> 3569inline 3570typename basic_string<_CharT, _Traits, _Allocator>::size_type 3571basic_string<_CharT, _Traits, _Allocator>::rfind(const basic_string& __str, 3572 size_type __pos) const _NOEXCEPT 3573{ 3574 return __str_rfind<value_type, size_type, traits_type, npos> 3575 (data(), size(), __str.data(), __pos, __str.size()); 3576} 3577 3578template<class _CharT, class _Traits, class _Allocator> 3579template <class _Tp> 3580_EnableIf 3581< 3582 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3583 typename basic_string<_CharT, _Traits, _Allocator>::size_type 3584> 3585basic_string<_CharT, _Traits, _Allocator>::rfind(const _Tp& __t, 3586 size_type __pos) const 3587{ 3588 __self_view __sv = __t; 3589 return __str_rfind<value_type, size_type, traits_type, npos> 3590 (data(), size(), __sv.data(), __pos, __sv.size()); 3591} 3592 3593template<class _CharT, class _Traits, class _Allocator> 3594inline 3595typename basic_string<_CharT, _Traits, _Allocator>::size_type 3596basic_string<_CharT, _Traits, _Allocator>::rfind(const value_type* __s, 3597 size_type __pos) const _NOEXCEPT 3598{ 3599 _LIBCPP_ASSERT(__s != nullptr, "string::rfind(): received nullptr"); 3600 return __str_rfind<value_type, size_type, traits_type, npos> 3601 (data(), size(), __s, __pos, traits_type::length(__s)); 3602} 3603 3604template<class _CharT, class _Traits, class _Allocator> 3605typename basic_string<_CharT, _Traits, _Allocator>::size_type 3606basic_string<_CharT, _Traits, _Allocator>::rfind(value_type __c, 3607 size_type __pos) const _NOEXCEPT 3608{ 3609 return __str_rfind<value_type, size_type, traits_type, npos> 3610 (data(), size(), __c, __pos); 3611} 3612 3613// find_first_of 3614 3615template<class _CharT, class _Traits, class _Allocator> 3616typename basic_string<_CharT, _Traits, _Allocator>::size_type 3617basic_string<_CharT, _Traits, _Allocator>::find_first_of(const value_type* __s, 3618 size_type __pos, 3619 size_type __n) const _NOEXCEPT 3620{ 3621 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_first_of(): received nullptr"); 3622 return __str_find_first_of<value_type, size_type, traits_type, npos> 3623 (data(), size(), __s, __pos, __n); 3624} 3625 3626template<class _CharT, class _Traits, class _Allocator> 3627inline 3628typename basic_string<_CharT, _Traits, _Allocator>::size_type 3629basic_string<_CharT, _Traits, _Allocator>::find_first_of(const basic_string& __str, 3630 size_type __pos) const _NOEXCEPT 3631{ 3632 return __str_find_first_of<value_type, size_type, traits_type, npos> 3633 (data(), size(), __str.data(), __pos, __str.size()); 3634} 3635 3636template<class _CharT, class _Traits, class _Allocator> 3637template <class _Tp> 3638_EnableIf 3639< 3640 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3641 typename basic_string<_CharT, _Traits, _Allocator>::size_type 3642> 3643basic_string<_CharT, _Traits, _Allocator>::find_first_of(const _Tp& __t, 3644 size_type __pos) const 3645{ 3646 __self_view __sv = __t; 3647 return __str_find_first_of<value_type, size_type, traits_type, npos> 3648 (data(), size(), __sv.data(), __pos, __sv.size()); 3649} 3650 3651template<class _CharT, class _Traits, class _Allocator> 3652inline 3653typename basic_string<_CharT, _Traits, _Allocator>::size_type 3654basic_string<_CharT, _Traits, _Allocator>::find_first_of(const value_type* __s, 3655 size_type __pos) const _NOEXCEPT 3656{ 3657 _LIBCPP_ASSERT(__s != nullptr, "string::find_first_of(): received nullptr"); 3658 return __str_find_first_of<value_type, size_type, traits_type, npos> 3659 (data(), size(), __s, __pos, traits_type::length(__s)); 3660} 3661 3662template<class _CharT, class _Traits, class _Allocator> 3663inline 3664typename basic_string<_CharT, _Traits, _Allocator>::size_type 3665basic_string<_CharT, _Traits, _Allocator>::find_first_of(value_type __c, 3666 size_type __pos) const _NOEXCEPT 3667{ 3668 return find(__c, __pos); 3669} 3670 3671// find_last_of 3672 3673template<class _CharT, class _Traits, class _Allocator> 3674typename basic_string<_CharT, _Traits, _Allocator>::size_type 3675basic_string<_CharT, _Traits, _Allocator>::find_last_of(const value_type* __s, 3676 size_type __pos, 3677 size_type __n) const _NOEXCEPT 3678{ 3679 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_last_of(): received nullptr"); 3680 return __str_find_last_of<value_type, size_type, traits_type, npos> 3681 (data(), size(), __s, __pos, __n); 3682} 3683 3684template<class _CharT, class _Traits, class _Allocator> 3685inline 3686typename basic_string<_CharT, _Traits, _Allocator>::size_type 3687basic_string<_CharT, _Traits, _Allocator>::find_last_of(const basic_string& __str, 3688 size_type __pos) const _NOEXCEPT 3689{ 3690 return __str_find_last_of<value_type, size_type, traits_type, npos> 3691 (data(), size(), __str.data(), __pos, __str.size()); 3692} 3693 3694template<class _CharT, class _Traits, class _Allocator> 3695template <class _Tp> 3696_EnableIf 3697< 3698 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3699 typename basic_string<_CharT, _Traits, _Allocator>::size_type 3700> 3701basic_string<_CharT, _Traits, _Allocator>::find_last_of(const _Tp& __t, 3702 size_type __pos) const 3703{ 3704 __self_view __sv = __t; 3705 return __str_find_last_of<value_type, size_type, traits_type, npos> 3706 (data(), size(), __sv.data(), __pos, __sv.size()); 3707} 3708 3709template<class _CharT, class _Traits, class _Allocator> 3710inline 3711typename basic_string<_CharT, _Traits, _Allocator>::size_type 3712basic_string<_CharT, _Traits, _Allocator>::find_last_of(const value_type* __s, 3713 size_type __pos) const _NOEXCEPT 3714{ 3715 _LIBCPP_ASSERT(__s != nullptr, "string::find_last_of(): received nullptr"); 3716 return __str_find_last_of<value_type, size_type, traits_type, npos> 3717 (data(), size(), __s, __pos, traits_type::length(__s)); 3718} 3719 3720template<class _CharT, class _Traits, class _Allocator> 3721inline 3722typename basic_string<_CharT, _Traits, _Allocator>::size_type 3723basic_string<_CharT, _Traits, _Allocator>::find_last_of(value_type __c, 3724 size_type __pos) const _NOEXCEPT 3725{ 3726 return rfind(__c, __pos); 3727} 3728 3729// find_first_not_of 3730 3731template<class _CharT, class _Traits, class _Allocator> 3732typename basic_string<_CharT, _Traits, _Allocator>::size_type 3733basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(const value_type* __s, 3734 size_type __pos, 3735 size_type __n) const _NOEXCEPT 3736{ 3737 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_first_not_of(): received nullptr"); 3738 return __str_find_first_not_of<value_type, size_type, traits_type, npos> 3739 (data(), size(), __s, __pos, __n); 3740} 3741 3742template<class _CharT, class _Traits, class _Allocator> 3743inline 3744typename basic_string<_CharT, _Traits, _Allocator>::size_type 3745basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(const basic_string& __str, 3746 size_type __pos) const _NOEXCEPT 3747{ 3748 return __str_find_first_not_of<value_type, size_type, traits_type, npos> 3749 (data(), size(), __str.data(), __pos, __str.size()); 3750} 3751 3752template<class _CharT, class _Traits, class _Allocator> 3753template <class _Tp> 3754_EnableIf 3755< 3756 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3757 typename basic_string<_CharT, _Traits, _Allocator>::size_type 3758> 3759basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(const _Tp& __t, 3760 size_type __pos) const 3761{ 3762 __self_view __sv = __t; 3763 return __str_find_first_not_of<value_type, size_type, traits_type, npos> 3764 (data(), size(), __sv.data(), __pos, __sv.size()); 3765} 3766 3767template<class _CharT, class _Traits, class _Allocator> 3768inline 3769typename basic_string<_CharT, _Traits, _Allocator>::size_type 3770basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(const value_type* __s, 3771 size_type __pos) const _NOEXCEPT 3772{ 3773 _LIBCPP_ASSERT(__s != nullptr, "string::find_first_not_of(): received nullptr"); 3774 return __str_find_first_not_of<value_type, size_type, traits_type, npos> 3775 (data(), size(), __s, __pos, traits_type::length(__s)); 3776} 3777 3778template<class _CharT, class _Traits, class _Allocator> 3779inline 3780typename basic_string<_CharT, _Traits, _Allocator>::size_type 3781basic_string<_CharT, _Traits, _Allocator>::find_first_not_of(value_type __c, 3782 size_type __pos) const _NOEXCEPT 3783{ 3784 return __str_find_first_not_of<value_type, size_type, traits_type, npos> 3785 (data(), size(), __c, __pos); 3786} 3787 3788// find_last_not_of 3789 3790template<class _CharT, class _Traits, class _Allocator> 3791typename basic_string<_CharT, _Traits, _Allocator>::size_type 3792basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(const value_type* __s, 3793 size_type __pos, 3794 size_type __n) const _NOEXCEPT 3795{ 3796 _LIBCPP_ASSERT(__n == 0 || __s != nullptr, "string::find_last_not_of(): received nullptr"); 3797 return __str_find_last_not_of<value_type, size_type, traits_type, npos> 3798 (data(), size(), __s, __pos, __n); 3799} 3800 3801template<class _CharT, class _Traits, class _Allocator> 3802inline 3803typename basic_string<_CharT, _Traits, _Allocator>::size_type 3804basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(const basic_string& __str, 3805 size_type __pos) const _NOEXCEPT 3806{ 3807 return __str_find_last_not_of<value_type, size_type, traits_type, npos> 3808 (data(), size(), __str.data(), __pos, __str.size()); 3809} 3810 3811template<class _CharT, class _Traits, class _Allocator> 3812template <class _Tp> 3813_EnableIf 3814< 3815 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3816 typename basic_string<_CharT, _Traits, _Allocator>::size_type 3817> 3818basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(const _Tp& __t, 3819 size_type __pos) const 3820{ 3821 __self_view __sv = __t; 3822 return __str_find_last_not_of<value_type, size_type, traits_type, npos> 3823 (data(), size(), __sv.data(), __pos, __sv.size()); 3824} 3825 3826template<class _CharT, class _Traits, class _Allocator> 3827inline 3828typename basic_string<_CharT, _Traits, _Allocator>::size_type 3829basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(const value_type* __s, 3830 size_type __pos) const _NOEXCEPT 3831{ 3832 _LIBCPP_ASSERT(__s != nullptr, "string::find_last_not_of(): received nullptr"); 3833 return __str_find_last_not_of<value_type, size_type, traits_type, npos> 3834 (data(), size(), __s, __pos, traits_type::length(__s)); 3835} 3836 3837template<class _CharT, class _Traits, class _Allocator> 3838inline 3839typename basic_string<_CharT, _Traits, _Allocator>::size_type 3840basic_string<_CharT, _Traits, _Allocator>::find_last_not_of(value_type __c, 3841 size_type __pos) const _NOEXCEPT 3842{ 3843 return __str_find_last_not_of<value_type, size_type, traits_type, npos> 3844 (data(), size(), __c, __pos); 3845} 3846 3847// compare 3848 3849template <class _CharT, class _Traits, class _Allocator> 3850template <class _Tp> 3851_EnableIf 3852< 3853 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3854 int 3855> 3856basic_string<_CharT, _Traits, _Allocator>::compare(const _Tp& __t) const 3857{ 3858 __self_view __sv = __t; 3859 size_t __lhs_sz = size(); 3860 size_t __rhs_sz = __sv.size(); 3861 int __result = traits_type::compare(data(), __sv.data(), 3862 _VSTD::min(__lhs_sz, __rhs_sz)); 3863 if (__result != 0) 3864 return __result; 3865 if (__lhs_sz < __rhs_sz) 3866 return -1; 3867 if (__lhs_sz > __rhs_sz) 3868 return 1; 3869 return 0; 3870} 3871 3872template <class _CharT, class _Traits, class _Allocator> 3873inline 3874int 3875basic_string<_CharT, _Traits, _Allocator>::compare(const basic_string& __str) const _NOEXCEPT 3876{ 3877 return compare(__self_view(__str)); 3878} 3879 3880template <class _CharT, class _Traits, class _Allocator> 3881int 3882basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1, 3883 size_type __n1, 3884 const value_type* __s, 3885 size_type __n2) const 3886{ 3887 _LIBCPP_ASSERT(__n2 == 0 || __s != nullptr, "string::compare(): received nullptr"); 3888 size_type __sz = size(); 3889 if (__pos1 > __sz || __n2 == npos) 3890 this->__throw_out_of_range(); 3891 size_type __rlen = _VSTD::min(__n1, __sz - __pos1); 3892 int __r = traits_type::compare(data() + __pos1, __s, _VSTD::min(__rlen, __n2)); 3893 if (__r == 0) 3894 { 3895 if (__rlen < __n2) 3896 __r = -1; 3897 else if (__rlen > __n2) 3898 __r = 1; 3899 } 3900 return __r; 3901} 3902 3903template <class _CharT, class _Traits, class _Allocator> 3904template <class _Tp> 3905_EnableIf 3906< 3907 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value, 3908 int 3909> 3910basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1, 3911 size_type __n1, 3912 const _Tp& __t) const 3913{ 3914 __self_view __sv = __t; 3915 return compare(__pos1, __n1, __sv.data(), __sv.size()); 3916} 3917 3918template <class _CharT, class _Traits, class _Allocator> 3919inline 3920int 3921basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1, 3922 size_type __n1, 3923 const basic_string& __str) const 3924{ 3925 return compare(__pos1, __n1, __str.data(), __str.size()); 3926} 3927 3928template <class _CharT, class _Traits, class _Allocator> 3929template <class _Tp> 3930_EnableIf 3931< 3932 __can_be_converted_to_string_view<_CharT, _Traits, _Tp>::value 3933 && !__is_same_uncvref<_Tp, basic_string<_CharT, _Traits, _Allocator> >::value, 3934 int 3935> 3936basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1, 3937 size_type __n1, 3938 const _Tp& __t, 3939 size_type __pos2, 3940 size_type __n2) const 3941{ 3942 __self_view __sv = __t; 3943 return __self_view(*this).substr(__pos1, __n1).compare(__sv.substr(__pos2, __n2)); 3944} 3945 3946template <class _CharT, class _Traits, class _Allocator> 3947int 3948basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1, 3949 size_type __n1, 3950 const basic_string& __str, 3951 size_type __pos2, 3952 size_type __n2) const 3953{ 3954 return compare(__pos1, __n1, __self_view(__str), __pos2, __n2); 3955} 3956 3957template <class _CharT, class _Traits, class _Allocator> 3958int 3959basic_string<_CharT, _Traits, _Allocator>::compare(const value_type* __s) const _NOEXCEPT 3960{ 3961 _LIBCPP_ASSERT(__s != nullptr, "string::compare(): received nullptr"); 3962 return compare(0, npos, __s, traits_type::length(__s)); 3963} 3964 3965template <class _CharT, class _Traits, class _Allocator> 3966int 3967basic_string<_CharT, _Traits, _Allocator>::compare(size_type __pos1, 3968 size_type __n1, 3969 const value_type* __s) const 3970{ 3971 _LIBCPP_ASSERT(__s != nullptr, "string::compare(): received nullptr"); 3972 return compare(__pos1, __n1, __s, traits_type::length(__s)); 3973} 3974 3975// __invariants 3976 3977template<class _CharT, class _Traits, class _Allocator> 3978inline 3979bool 3980basic_string<_CharT, _Traits, _Allocator>::__invariants() const 3981{ 3982 if (size() > capacity()) 3983 return false; 3984 if (capacity() < __min_cap - 1) 3985 return false; 3986 if (data() == nullptr) 3987 return false; 3988 if (data()[size()] != value_type()) 3989 return false; 3990 return true; 3991} 3992 3993// __clear_and_shrink 3994 3995template<class _CharT, class _Traits, class _Allocator> 3996inline 3997void 3998basic_string<_CharT, _Traits, _Allocator>::__clear_and_shrink() _NOEXCEPT 3999{ 4000 clear(); 4001 if(__is_long()) 4002 { 4003 __alloc_traits::deallocate(__alloc(), __get_long_pointer(), capacity() + 1); 4004 __set_long_cap(0); 4005 __set_short_size(0); 4006 traits_type::assign(*__get_short_pointer(), value_type()); 4007 } 4008} 4009 4010// operator== 4011 4012template<class _CharT, class _Traits, class _Allocator> 4013inline _LIBCPP_INLINE_VISIBILITY 4014bool 4015operator==(const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4016 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4017{ 4018 size_t __lhs_sz = __lhs.size(); 4019 return __lhs_sz == __rhs.size() && _Traits::compare(__lhs.data(), 4020 __rhs.data(), 4021 __lhs_sz) == 0; 4022} 4023 4024template<class _Allocator> 4025inline _LIBCPP_INLINE_VISIBILITY 4026bool 4027operator==(const basic_string<char, char_traits<char>, _Allocator>& __lhs, 4028 const basic_string<char, char_traits<char>, _Allocator>& __rhs) _NOEXCEPT 4029{ 4030 size_t __lhs_sz = __lhs.size(); 4031 if (__lhs_sz != __rhs.size()) 4032 return false; 4033 const char* __lp = __lhs.data(); 4034 const char* __rp = __rhs.data(); 4035 if (__lhs.__is_long()) 4036 return char_traits<char>::compare(__lp, __rp, __lhs_sz) == 0; 4037 for (; __lhs_sz != 0; --__lhs_sz, ++__lp, ++__rp) 4038 if (*__lp != *__rp) 4039 return false; 4040 return true; 4041} 4042 4043template<class _CharT, class _Traits, class _Allocator> 4044inline _LIBCPP_INLINE_VISIBILITY 4045bool 4046operator==(const _CharT* __lhs, 4047 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4048{ 4049 typedef basic_string<_CharT, _Traits, _Allocator> _String; 4050 _LIBCPP_ASSERT(__lhs != nullptr, "operator==(char*, basic_string): received nullptr"); 4051 size_t __lhs_len = _Traits::length(__lhs); 4052 if (__lhs_len != __rhs.size()) return false; 4053 return __rhs.compare(0, _String::npos, __lhs, __lhs_len) == 0; 4054} 4055 4056template<class _CharT, class _Traits, class _Allocator> 4057inline _LIBCPP_INLINE_VISIBILITY 4058bool 4059operator==(const basic_string<_CharT,_Traits,_Allocator>& __lhs, 4060 const _CharT* __rhs) _NOEXCEPT 4061{ 4062 typedef basic_string<_CharT, _Traits, _Allocator> _String; 4063 _LIBCPP_ASSERT(__rhs != nullptr, "operator==(basic_string, char*): received nullptr"); 4064 size_t __rhs_len = _Traits::length(__rhs); 4065 if (__rhs_len != __lhs.size()) return false; 4066 return __lhs.compare(0, _String::npos, __rhs, __rhs_len) == 0; 4067} 4068 4069template<class _CharT, class _Traits, class _Allocator> 4070inline _LIBCPP_INLINE_VISIBILITY 4071bool 4072operator!=(const basic_string<_CharT,_Traits,_Allocator>& __lhs, 4073 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4074{ 4075 return !(__lhs == __rhs); 4076} 4077 4078template<class _CharT, class _Traits, class _Allocator> 4079inline _LIBCPP_INLINE_VISIBILITY 4080bool 4081operator!=(const _CharT* __lhs, 4082 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4083{ 4084 return !(__lhs == __rhs); 4085} 4086 4087template<class _CharT, class _Traits, class _Allocator> 4088inline _LIBCPP_INLINE_VISIBILITY 4089bool 4090operator!=(const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4091 const _CharT* __rhs) _NOEXCEPT 4092{ 4093 return !(__lhs == __rhs); 4094} 4095 4096// operator< 4097 4098template<class _CharT, class _Traits, class _Allocator> 4099inline _LIBCPP_INLINE_VISIBILITY 4100bool 4101operator< (const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4102 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4103{ 4104 return __lhs.compare(__rhs) < 0; 4105} 4106 4107template<class _CharT, class _Traits, class _Allocator> 4108inline _LIBCPP_INLINE_VISIBILITY 4109bool 4110operator< (const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4111 const _CharT* __rhs) _NOEXCEPT 4112{ 4113 return __lhs.compare(__rhs) < 0; 4114} 4115 4116template<class _CharT, class _Traits, class _Allocator> 4117inline _LIBCPP_INLINE_VISIBILITY 4118bool 4119operator< (const _CharT* __lhs, 4120 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4121{ 4122 return __rhs.compare(__lhs) > 0; 4123} 4124 4125// operator> 4126 4127template<class _CharT, class _Traits, class _Allocator> 4128inline _LIBCPP_INLINE_VISIBILITY 4129bool 4130operator> (const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4131 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4132{ 4133 return __rhs < __lhs; 4134} 4135 4136template<class _CharT, class _Traits, class _Allocator> 4137inline _LIBCPP_INLINE_VISIBILITY 4138bool 4139operator> (const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4140 const _CharT* __rhs) _NOEXCEPT 4141{ 4142 return __rhs < __lhs; 4143} 4144 4145template<class _CharT, class _Traits, class _Allocator> 4146inline _LIBCPP_INLINE_VISIBILITY 4147bool 4148operator> (const _CharT* __lhs, 4149 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4150{ 4151 return __rhs < __lhs; 4152} 4153 4154// operator<= 4155 4156template<class _CharT, class _Traits, class _Allocator> 4157inline _LIBCPP_INLINE_VISIBILITY 4158bool 4159operator<=(const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4160 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4161{ 4162 return !(__rhs < __lhs); 4163} 4164 4165template<class _CharT, class _Traits, class _Allocator> 4166inline _LIBCPP_INLINE_VISIBILITY 4167bool 4168operator<=(const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4169 const _CharT* __rhs) _NOEXCEPT 4170{ 4171 return !(__rhs < __lhs); 4172} 4173 4174template<class _CharT, class _Traits, class _Allocator> 4175inline _LIBCPP_INLINE_VISIBILITY 4176bool 4177operator<=(const _CharT* __lhs, 4178 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4179{ 4180 return !(__rhs < __lhs); 4181} 4182 4183// operator>= 4184 4185template<class _CharT, class _Traits, class _Allocator> 4186inline _LIBCPP_INLINE_VISIBILITY 4187bool 4188operator>=(const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4189 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4190{ 4191 return !(__lhs < __rhs); 4192} 4193 4194template<class _CharT, class _Traits, class _Allocator> 4195inline _LIBCPP_INLINE_VISIBILITY 4196bool 4197operator>=(const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4198 const _CharT* __rhs) _NOEXCEPT 4199{ 4200 return !(__lhs < __rhs); 4201} 4202 4203template<class _CharT, class _Traits, class _Allocator> 4204inline _LIBCPP_INLINE_VISIBILITY 4205bool 4206operator>=(const _CharT* __lhs, 4207 const basic_string<_CharT, _Traits, _Allocator>& __rhs) _NOEXCEPT 4208{ 4209 return !(__lhs < __rhs); 4210} 4211 4212// operator + 4213 4214template<class _CharT, class _Traits, class _Allocator> 4215basic_string<_CharT, _Traits, _Allocator> 4216operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs, 4217 const basic_string<_CharT, _Traits, _Allocator>& __rhs) 4218{ 4219 basic_string<_CharT, _Traits, _Allocator> __r(__lhs.get_allocator()); 4220 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = __lhs.size(); 4221 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = __rhs.size(); 4222 __r.__init(__lhs.data(), __lhs_sz, __lhs_sz + __rhs_sz); 4223 __r.append(__rhs.data(), __rhs_sz); 4224 return __r; 4225} 4226 4227template<class _CharT, class _Traits, class _Allocator> 4228basic_string<_CharT, _Traits, _Allocator> 4229operator+(const _CharT* __lhs , const basic_string<_CharT,_Traits,_Allocator>& __rhs) 4230{ 4231 basic_string<_CharT, _Traits, _Allocator> __r(__rhs.get_allocator()); 4232 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = _Traits::length(__lhs); 4233 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = __rhs.size(); 4234 __r.__init(__lhs, __lhs_sz, __lhs_sz + __rhs_sz); 4235 __r.append(__rhs.data(), __rhs_sz); 4236 return __r; 4237} 4238 4239template<class _CharT, class _Traits, class _Allocator> 4240basic_string<_CharT, _Traits, _Allocator> 4241operator+(_CharT __lhs, const basic_string<_CharT,_Traits,_Allocator>& __rhs) 4242{ 4243 basic_string<_CharT, _Traits, _Allocator> __r(__rhs.get_allocator()); 4244 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = __rhs.size(); 4245 __r.__init(&__lhs, 1, 1 + __rhs_sz); 4246 __r.append(__rhs.data(), __rhs_sz); 4247 return __r; 4248} 4249 4250template<class _CharT, class _Traits, class _Allocator> 4251inline 4252basic_string<_CharT, _Traits, _Allocator> 4253operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs, const _CharT* __rhs) 4254{ 4255 basic_string<_CharT, _Traits, _Allocator> __r(__lhs.get_allocator()); 4256 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = __lhs.size(); 4257 typename basic_string<_CharT, _Traits, _Allocator>::size_type __rhs_sz = _Traits::length(__rhs); 4258 __r.__init(__lhs.data(), __lhs_sz, __lhs_sz + __rhs_sz); 4259 __r.append(__rhs, __rhs_sz); 4260 return __r; 4261} 4262 4263template<class _CharT, class _Traits, class _Allocator> 4264basic_string<_CharT, _Traits, _Allocator> 4265operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs, _CharT __rhs) 4266{ 4267 basic_string<_CharT, _Traits, _Allocator> __r(__lhs.get_allocator()); 4268 typename basic_string<_CharT, _Traits, _Allocator>::size_type __lhs_sz = __lhs.size(); 4269 __r.__init(__lhs.data(), __lhs_sz, __lhs_sz + 1); 4270 __r.push_back(__rhs); 4271 return __r; 4272} 4273 4274#ifndef _LIBCPP_CXX03_LANG 4275 4276template<class _CharT, class _Traits, class _Allocator> 4277inline _LIBCPP_INLINE_VISIBILITY 4278basic_string<_CharT, _Traits, _Allocator> 4279operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, const basic_string<_CharT, _Traits, _Allocator>& __rhs) 4280{ 4281 return _VSTD::move(__lhs.append(__rhs)); 4282} 4283 4284template<class _CharT, class _Traits, class _Allocator> 4285inline _LIBCPP_INLINE_VISIBILITY 4286basic_string<_CharT, _Traits, _Allocator> 4287operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs, basic_string<_CharT, _Traits, _Allocator>&& __rhs) 4288{ 4289 return _VSTD::move(__rhs.insert(0, __lhs)); 4290} 4291 4292template<class _CharT, class _Traits, class _Allocator> 4293inline _LIBCPP_INLINE_VISIBILITY 4294basic_string<_CharT, _Traits, _Allocator> 4295operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, basic_string<_CharT, _Traits, _Allocator>&& __rhs) 4296{ 4297 return _VSTD::move(__lhs.append(__rhs)); 4298} 4299 4300template<class _CharT, class _Traits, class _Allocator> 4301inline _LIBCPP_INLINE_VISIBILITY 4302basic_string<_CharT, _Traits, _Allocator> 4303operator+(const _CharT* __lhs , basic_string<_CharT,_Traits,_Allocator>&& __rhs) 4304{ 4305 return _VSTD::move(__rhs.insert(0, __lhs)); 4306} 4307 4308template<class _CharT, class _Traits, class _Allocator> 4309inline _LIBCPP_INLINE_VISIBILITY 4310basic_string<_CharT, _Traits, _Allocator> 4311operator+(_CharT __lhs, basic_string<_CharT,_Traits,_Allocator>&& __rhs) 4312{ 4313 __rhs.insert(__rhs.begin(), __lhs); 4314 return _VSTD::move(__rhs); 4315} 4316 4317template<class _CharT, class _Traits, class _Allocator> 4318inline _LIBCPP_INLINE_VISIBILITY 4319basic_string<_CharT, _Traits, _Allocator> 4320operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, const _CharT* __rhs) 4321{ 4322 return _VSTD::move(__lhs.append(__rhs)); 4323} 4324 4325template<class _CharT, class _Traits, class _Allocator> 4326inline _LIBCPP_INLINE_VISIBILITY 4327basic_string<_CharT, _Traits, _Allocator> 4328operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, _CharT __rhs) 4329{ 4330 __lhs.push_back(__rhs); 4331 return _VSTD::move(__lhs); 4332} 4333 4334#endif // _LIBCPP_CXX03_LANG 4335 4336// swap 4337 4338template<class _CharT, class _Traits, class _Allocator> 4339inline _LIBCPP_INLINE_VISIBILITY 4340void 4341swap(basic_string<_CharT, _Traits, _Allocator>& __lhs, 4342 basic_string<_CharT, _Traits, _Allocator>& __rhs) 4343 _NOEXCEPT_(_NOEXCEPT_(__lhs.swap(__rhs))) 4344{ 4345 __lhs.swap(__rhs); 4346} 4347 4348_LIBCPP_FUNC_VIS int stoi (const string& __str, size_t* __idx = nullptr, int __base = 10); 4349_LIBCPP_FUNC_VIS long stol (const string& __str, size_t* __idx = nullptr, int __base = 10); 4350_LIBCPP_FUNC_VIS unsigned long stoul (const string& __str, size_t* __idx = nullptr, int __base = 10); 4351_LIBCPP_FUNC_VIS long long stoll (const string& __str, size_t* __idx = nullptr, int __base = 10); 4352_LIBCPP_FUNC_VIS unsigned long long stoull(const string& __str, size_t* __idx = nullptr, int __base = 10); 4353 4354_LIBCPP_FUNC_VIS float stof (const string& __str, size_t* __idx = nullptr); 4355_LIBCPP_FUNC_VIS double stod (const string& __str, size_t* __idx = nullptr); 4356_LIBCPP_FUNC_VIS long double stold(const string& __str, size_t* __idx = nullptr); 4357 4358_LIBCPP_FUNC_VIS string to_string(int __val); 4359_LIBCPP_FUNC_VIS string to_string(unsigned __val); 4360_LIBCPP_FUNC_VIS string to_string(long __val); 4361_LIBCPP_FUNC_VIS string to_string(unsigned long __val); 4362_LIBCPP_FUNC_VIS string to_string(long long __val); 4363_LIBCPP_FUNC_VIS string to_string(unsigned long long __val); 4364_LIBCPP_FUNC_VIS string to_string(float __val); 4365_LIBCPP_FUNC_VIS string to_string(double __val); 4366_LIBCPP_FUNC_VIS string to_string(long double __val); 4367 4368_LIBCPP_FUNC_VIS int stoi (const wstring& __str, size_t* __idx = nullptr, int __base = 10); 4369_LIBCPP_FUNC_VIS long stol (const wstring& __str, size_t* __idx = nullptr, int __base = 10); 4370_LIBCPP_FUNC_VIS unsigned long stoul (const wstring& __str, size_t* __idx = nullptr, int __base = 10); 4371_LIBCPP_FUNC_VIS long long stoll (const wstring& __str, size_t* __idx = nullptr, int __base = 10); 4372_LIBCPP_FUNC_VIS unsigned long long stoull(const wstring& __str, size_t* __idx = nullptr, int __base = 10); 4373 4374_LIBCPP_FUNC_VIS float stof (const wstring& __str, size_t* __idx = nullptr); 4375_LIBCPP_FUNC_VIS double stod (const wstring& __str, size_t* __idx = nullptr); 4376_LIBCPP_FUNC_VIS long double stold(const wstring& __str, size_t* __idx = nullptr); 4377 4378_LIBCPP_FUNC_VIS wstring to_wstring(int __val); 4379_LIBCPP_FUNC_VIS wstring to_wstring(unsigned __val); 4380_LIBCPP_FUNC_VIS wstring to_wstring(long __val); 4381_LIBCPP_FUNC_VIS wstring to_wstring(unsigned long __val); 4382_LIBCPP_FUNC_VIS wstring to_wstring(long long __val); 4383_LIBCPP_FUNC_VIS wstring to_wstring(unsigned long long __val); 4384_LIBCPP_FUNC_VIS wstring to_wstring(float __val); 4385_LIBCPP_FUNC_VIS wstring to_wstring(double __val); 4386_LIBCPP_FUNC_VIS wstring to_wstring(long double __val); 4387 4388template<class _CharT, class _Traits, class _Allocator> 4389_LIBCPP_FUNC_VIS 4390const typename basic_string<_CharT, _Traits, _Allocator>::size_type 4391 basic_string<_CharT, _Traits, _Allocator>::npos; 4392 4393template <class _CharT, class _Allocator> 4394struct _LIBCPP_TEMPLATE_VIS 4395 hash<basic_string<_CharT, char_traits<_CharT>, _Allocator> > 4396 : public unary_function< 4397 basic_string<_CharT, char_traits<_CharT>, _Allocator>, size_t> 4398{ 4399 size_t 4400 operator()(const basic_string<_CharT, char_traits<_CharT>, _Allocator>& __val) const _NOEXCEPT 4401 { return __do_string_hash(__val.data(), __val.data() + __val.size()); } 4402}; 4403 4404 4405template<class _CharT, class _Traits, class _Allocator> 4406basic_ostream<_CharT, _Traits>& 4407operator<<(basic_ostream<_CharT, _Traits>& __os, 4408 const basic_string<_CharT, _Traits, _Allocator>& __str); 4409 4410template<class _CharT, class _Traits, class _Allocator> 4411basic_istream<_CharT, _Traits>& 4412operator>>(basic_istream<_CharT, _Traits>& __is, 4413 basic_string<_CharT, _Traits, _Allocator>& __str); 4414 4415template<class _CharT, class _Traits, class _Allocator> 4416basic_istream<_CharT, _Traits>& 4417getline(basic_istream<_CharT, _Traits>& __is, 4418 basic_string<_CharT, _Traits, _Allocator>& __str, _CharT __dlm); 4419 4420template<class _CharT, class _Traits, class _Allocator> 4421inline _LIBCPP_INLINE_VISIBILITY 4422basic_istream<_CharT, _Traits>& 4423getline(basic_istream<_CharT, _Traits>& __is, 4424 basic_string<_CharT, _Traits, _Allocator>& __str); 4425 4426#ifndef _LIBCPP_CXX03_LANG 4427 4428template<class _CharT, class _Traits, class _Allocator> 4429inline _LIBCPP_INLINE_VISIBILITY 4430basic_istream<_CharT, _Traits>& 4431getline(basic_istream<_CharT, _Traits>&& __is, 4432 basic_string<_CharT, _Traits, _Allocator>& __str, _CharT __dlm); 4433 4434template<class _CharT, class _Traits, class _Allocator> 4435inline _LIBCPP_INLINE_VISIBILITY 4436basic_istream<_CharT, _Traits>& 4437getline(basic_istream<_CharT, _Traits>&& __is, 4438 basic_string<_CharT, _Traits, _Allocator>& __str); 4439 4440#endif // _LIBCPP_CXX03_LANG 4441 4442#if _LIBCPP_STD_VER > 17 4443template <class _CharT, class _Traits, class _Allocator, class _Up> 4444inline _LIBCPP_INLINE_VISIBILITY 4445 typename basic_string<_CharT, _Traits, _Allocator>::size_type 4446 erase(basic_string<_CharT, _Traits, _Allocator>& __str, const _Up& __v) { 4447 auto __old_size = __str.size(); 4448 __str.erase(_VSTD::remove(__str.begin(), __str.end(), __v), __str.end()); 4449 return __old_size - __str.size(); 4450} 4451 4452template <class _CharT, class _Traits, class _Allocator, class _Predicate> 4453inline _LIBCPP_INLINE_VISIBILITY 4454 typename basic_string<_CharT, _Traits, _Allocator>::size_type 4455 erase_if(basic_string<_CharT, _Traits, _Allocator>& __str, 4456 _Predicate __pred) { 4457 auto __old_size = __str.size(); 4458 __str.erase(_VSTD::remove_if(__str.begin(), __str.end(), __pred), 4459 __str.end()); 4460 return __old_size - __str.size(); 4461} 4462#endif 4463 4464#if _LIBCPP_DEBUG_LEVEL == 2 4465 4466template<class _CharT, class _Traits, class _Allocator> 4467bool 4468basic_string<_CharT, _Traits, _Allocator>::__dereferenceable(const const_iterator* __i) const 4469{ 4470 return this->data() <= _VSTD::__to_address(__i->base()) && 4471 _VSTD::__to_address(__i->base()) < this->data() + this->size(); 4472} 4473 4474template<class _CharT, class _Traits, class _Allocator> 4475bool 4476basic_string<_CharT, _Traits, _Allocator>::__decrementable(const const_iterator* __i) const 4477{ 4478 return this->data() < _VSTD::__to_address(__i->base()) && 4479 _VSTD::__to_address(__i->base()) <= this->data() + this->size(); 4480} 4481 4482template<class _CharT, class _Traits, class _Allocator> 4483bool 4484basic_string<_CharT, _Traits, _Allocator>::__addable(const const_iterator* __i, ptrdiff_t __n) const 4485{ 4486 const value_type* __p = _VSTD::__to_address(__i->base()) + __n; 4487 return this->data() <= __p && __p <= this->data() + this->size(); 4488} 4489 4490template<class _CharT, class _Traits, class _Allocator> 4491bool 4492basic_string<_CharT, _Traits, _Allocator>::__subscriptable(const const_iterator* __i, ptrdiff_t __n) const 4493{ 4494 const value_type* __p = _VSTD::__to_address(__i->base()) + __n; 4495 return this->data() <= __p && __p < this->data() + this->size(); 4496} 4497 4498#endif // _LIBCPP_DEBUG_LEVEL == 2 4499 4500#if _LIBCPP_STD_VER > 11 4501// Literal suffixes for basic_string [basic.string.literals] 4502inline namespace literals 4503{ 4504 inline namespace string_literals 4505 { 4506 inline _LIBCPP_INLINE_VISIBILITY 4507 basic_string<char> operator "" s( const char *__str, size_t __len ) 4508 { 4509 return basic_string<char> (__str, __len); 4510 } 4511 4512 inline _LIBCPP_INLINE_VISIBILITY 4513 basic_string<wchar_t> operator "" s( const wchar_t *__str, size_t __len ) 4514 { 4515 return basic_string<wchar_t> (__str, __len); 4516 } 4517 4518#ifndef _LIBCPP_NO_HAS_CHAR8_T 4519 inline _LIBCPP_INLINE_VISIBILITY 4520 basic_string<char8_t> operator "" s(const char8_t *__str, size_t __len) _NOEXCEPT 4521 { 4522 return basic_string<char8_t> (__str, __len); 4523 } 4524#endif 4525 4526 inline _LIBCPP_INLINE_VISIBILITY 4527 basic_string<char16_t> operator "" s( const char16_t *__str, size_t __len ) 4528 { 4529 return basic_string<char16_t> (__str, __len); 4530 } 4531 4532 inline _LIBCPP_INLINE_VISIBILITY 4533 basic_string<char32_t> operator "" s( const char32_t *__str, size_t __len ) 4534 { 4535 return basic_string<char32_t> (__str, __len); 4536 } 4537 } 4538} 4539#endif 4540 4541_LIBCPP_END_NAMESPACE_STD 4542 4543_LIBCPP_POP_MACROS 4544 4545#endif // _LIBCPP_STRING 4546