33 #ifndef _GLIBCXX_STRING_VIEW
34 #define _GLIBCXX_STRING_VIEW 1
36 #pragma GCC system_header
38 #if __cplusplus >= 201703L
48 namespace std _GLIBCXX_VISIBILITY(default)
50 _GLIBCXX_BEGIN_NAMESPACE_VERSION
52 # define __cpp_lib_string_view 201803L
53 #if __cplusplus > 201703L
54 # define __cpp_lib_constexpr_string_view 201811L
59 __sv_check(
size_t __size,
size_t __pos,
const char* __s)
62 __throw_out_of_range_fmt(__N(
"%s: __pos (which is %zu) > __size "
63 "(which is %zu)"), __s, __pos, __size);
70 __sv_limit(
size_t __size,
size_t __pos,
size_t __off) noexcept
72 const bool __testoff = __off < __size - __pos;
73 return __testoff ? __off : __size - __pos;
94 template<
typename _CharT,
typename _Traits = std::
char_traits<_CharT>>
97 static_assert(!is_array_v<_CharT>);
98 static_assert(is_trivial_v<_CharT> && is_standard_layout_v<_CharT>);
99 static_assert(is_same_v<_CharT, typename _Traits::char_type>);
104 using traits_type = _Traits;
105 using value_type = _CharT;
106 using pointer = value_type*;
107 using const_pointer =
const value_type*;
108 using reference = value_type&;
109 using const_reference =
const value_type&;
110 using const_iterator =
const value_type*;
111 using iterator = const_iterator;
114 using size_type = size_t;
115 using difference_type = ptrdiff_t;
116 static constexpr size_type npos = size_type(-1);
122 : _M_len{0}, _M_str{
nullptr}
127 __attribute__((__nonnull__)) constexpr
129 : _M_len{traits_type::length(__str)},
135 : _M_len{__len}, _M_str{__str}
138 #if __cplusplus > 201703L && __cpp_lib_concepts
139 template<contiguous_iterator _It, sized_sentinel_for<_It> _End>
140 requires same_as<iter_value_t<_It>, _CharT>
141 && (!convertible_to<_End, size_type>)
144 : _M_len(__last - __first), _M_str(std::to_address(__first))
153 constexpr const_iterator
154 begin()
const noexcept
155 {
return this->_M_str; }
157 constexpr const_iterator
159 {
return this->_M_str + this->_M_len; }
161 constexpr const_iterator
162 cbegin()
const noexcept
163 {
return this->_M_str; }
165 constexpr const_iterator
166 cend()
const noexcept
167 {
return this->_M_str + this->_M_len; }
170 rbegin()
const noexcept
174 rend()
const noexcept
178 crbegin()
const noexcept
182 crend()
const noexcept
188 size()
const noexcept
189 {
return this->_M_len; }
192 length()
const noexcept
196 max_size()
const noexcept
198 return (npos -
sizeof(size_type) -
sizeof(
void*))
199 /
sizeof(value_type) / 4;
202 [[nodiscard]] constexpr
bool
203 empty()
const noexcept
204 {
return this->_M_len == 0; }
208 constexpr const_reference
209 operator[](size_type __pos)
const noexcept
211 __glibcxx_assert(__pos < this->_M_len);
212 return *(this->_M_str + __pos);
215 constexpr const_reference
216 at(size_type __pos)
const
219 __throw_out_of_range_fmt(__N(
"basic_string_view::at: __pos "
220 "(which is %zu) >= this->size() "
221 "(which is %zu)"), __pos, this->size());
222 return *(this->_M_str + __pos);
225 constexpr const_reference
226 front()
const noexcept
228 __glibcxx_assert(this->_M_len > 0);
229 return *this->_M_str;
232 constexpr const_reference
233 back()
const noexcept
235 __glibcxx_assert(this->_M_len > 0);
236 return *(this->_M_str + this->_M_len - 1);
239 constexpr const_pointer
240 data()
const noexcept
241 {
return this->_M_str; }
246 remove_prefix(size_type __n) noexcept
248 __glibcxx_assert(this->_M_len >= __n);
254 remove_suffix(size_type __n) noexcept
255 { this->_M_len -= __n; }
269 copy(_CharT* __str, size_type __n, size_type __pos = 0)
const
271 __glibcxx_requires_string_len(__str, __n);
272 __pos = std::__sv_check(size(), __pos,
"basic_string_view::copy");
273 const size_type __rlen =
std::min(__n, _M_len - __pos);
276 traits_type::copy(__str, data() + __pos, __rlen);
281 substr(size_type __pos = 0, size_type __n = npos)
const noexcept(
false)
283 __pos = std::__sv_check(size(), __pos,
"basic_string_view::substr");
284 const size_type __rlen =
std::min(__n, _M_len - __pos);
291 const size_type __rlen =
std::min(this->_M_len, __str._M_len);
292 int __ret = traits_type::compare(this->_M_str, __str._M_str, __rlen);
294 __ret = _S_compare(this->_M_len, __str._M_len);
300 {
return this->substr(__pos1, __n1).compare(__str); }
303 compare(size_type __pos1, size_type __n1,
306 return this->substr(__pos1, __n1).compare(__str.substr(__pos2, __n2));
309 __attribute__((__nonnull__)) constexpr
int
310 compare(
const _CharT* __str)
const noexcept
313 __attribute__((__nonnull__)) constexpr
int
314 compare(size_type __pos1, size_type __n1,
const _CharT* __str)
const
318 compare(size_type __pos1, size_type __n1,
319 const _CharT* __str, size_type __n2)
const noexcept(
false)
321 return this->substr(__pos1, __n1)
325 #if __cplusplus > 201703L
326 #define __cpp_lib_starts_ends_with 201711L
329 {
return this->substr(0, __x.size()) == __x; }
332 starts_with(_CharT __x)
const noexcept
333 {
return !this->empty() && traits_type::eq(this->front(), __x); }
336 starts_with(
const _CharT* __x)
const noexcept
342 return this->size() >= __x.size()
343 && this->compare(this->size() - __x.size(), npos, __x) == 0;
347 ends_with(_CharT __x)
const noexcept
348 {
return !this->empty() && traits_type::eq(this->back(), __x); }
351 ends_with(
const _CharT* __x)
const noexcept
355 #if __cplusplus > 202002L
356 #define __cpp_lib_string_contains 202011L
359 {
return this->find(__x) != npos; }
362 contains(_CharT __x)
const noexcept
363 {
return this->find(__x) != npos; }
366 contains(
const _CharT* __x)
const noexcept
367 {
return this->find(__x) != npos; }
374 {
return this->find(__str._M_str, __pos, __str._M_len); }
377 find(_CharT __c, size_type __pos = 0)
const noexcept;
380 find(
const _CharT* __str, size_type __pos, size_type __n)
const noexcept;
382 __attribute__((__nonnull__)) constexpr size_type
383 find(
const _CharT* __str, size_type __pos = 0)
const noexcept
384 {
return this->find(__str, __pos, traits_type::length(__str)); }
388 {
return this->rfind(__str._M_str, __pos, __str._M_len); }
391 rfind(_CharT __c, size_type __pos = npos)
const noexcept;
394 rfind(
const _CharT* __str, size_type __pos, size_type __n)
const noexcept;
396 __attribute__((__nonnull__)) constexpr size_type
397 rfind(
const _CharT* __str, size_type __pos = npos)
const noexcept
398 {
return this->rfind(__str, __pos, traits_type::length(__str)); }
402 {
return this->find_first_of(__str._M_str, __pos, __str._M_len); }
405 find_first_of(_CharT __c, size_type __pos = 0)
const noexcept
406 {
return this->find(__c, __pos); }
409 find_first_of(
const _CharT* __str, size_type __pos,
410 size_type __n)
const noexcept;
412 __attribute__((__nonnull__)) constexpr size_type
413 find_first_of(
const _CharT* __str, size_type __pos = 0)
const noexcept
414 {
return this->find_first_of(__str, __pos, traits_type::length(__str)); }
418 size_type __pos = npos)
const noexcept
419 {
return this->find_last_of(__str._M_str, __pos, __str._M_len); }
422 find_last_of(_CharT __c, size_type __pos=npos)
const noexcept
423 {
return this->rfind(__c, __pos); }
426 find_last_of(
const _CharT* __str, size_type __pos,
427 size_type __n)
const noexcept;
429 __attribute__((__nonnull__)) constexpr size_type
430 find_last_of(
const _CharT* __str, size_type __pos = npos)
const noexcept
431 {
return this->find_last_of(__str, __pos, traits_type::length(__str)); }
435 size_type __pos = 0)
const noexcept
436 {
return this->find_first_not_of(__str._M_str, __pos, __str._M_len); }
439 find_first_not_of(_CharT __c, size_type __pos = 0)
const noexcept;
442 find_first_not_of(
const _CharT* __str,
443 size_type __pos, size_type __n)
const noexcept;
445 __attribute__((__nonnull__)) constexpr size_type
446 find_first_not_of(
const _CharT* __str, size_type __pos = 0)
const noexcept
448 return this->find_first_not_of(__str, __pos,
449 traits_type::length(__str));
454 size_type __pos = npos)
const noexcept
455 {
return this->find_last_not_of(__str._M_str, __pos, __str._M_len); }
458 find_last_not_of(_CharT __c, size_type __pos = npos)
const noexcept;
461 find_last_not_of(
const _CharT* __str,
462 size_type __pos, size_type __n)
const noexcept;
464 __attribute__((__nonnull__)) constexpr size_type
465 find_last_not_of(
const _CharT* __str,
466 size_type __pos = npos)
const noexcept
468 return this->find_last_not_of(__str, __pos,
469 traits_type::length(__str));
475 _S_compare(size_type __n1, size_type __n2) noexcept
478 const difference_type __diff = __n1 - __n2;
479 if (__diff > __limits::__max)
480 return __limits::__max;
481 if (__diff < __limits::__min)
482 return __limits::__min;
483 return static_cast<int>(__diff);
487 const _CharT* _M_str;
490 #if __cplusplus > 201703L && __cpp_lib_concepts && __cpp_deduction_guides
491 template<contiguous_iterator _It, sized_sentinel_for<_It> _End>
502 template<
typename _CharT,
typename _Traits>
506 {
return __x.size() == __y.size() && __x.compare(__y) == 0; }
508 template<
typename _CharT,
typename _Traits>
510 operator==(basic_string_view<_CharT, _Traits> __x,
511 __type_identity_t<basic_string_view<_CharT, _Traits>> __y)
513 {
return __x.size() == __y.size() && __x.compare(__y) == 0; }
515 #if __cpp_lib_three_way_comparison
516 template<
typename _CharT,
typename _Traits>
518 operator<=>(basic_string_view<_CharT, _Traits> __x,
519 basic_string_view<_CharT, _Traits> __y) noexcept
520 -> decltype(__detail::__char_traits_cmp_cat<_Traits>(0))
521 {
return __detail::__char_traits_cmp_cat<_Traits>(__x.compare(__y)); }
523 template<
typename _CharT,
typename _Traits>
525 operator<=>(basic_string_view<_CharT, _Traits> __x,
526 __type_identity_t<basic_string_view<_CharT, _Traits>> __y)
528 -> decltype(__detail::__char_traits_cmp_cat<_Traits>(0))
529 {
return __detail::__char_traits_cmp_cat<_Traits>(__x.compare(__y)); }
531 template<
typename _CharT,
typename _Traits>
533 operator==(__type_identity_t<basic_string_view<_CharT, _Traits>> __x,
534 basic_string_view<_CharT, _Traits> __y) noexcept
535 {
return __x.size() == __y.size() && __x.compare(__y) == 0; }
537 template<
typename _CharT,
typename _Traits>
539 operator!=(basic_string_view<_CharT, _Traits> __x,
540 basic_string_view<_CharT, _Traits> __y) noexcept
541 {
return !(__x == __y); }
543 template<
typename _CharT,
typename _Traits>
545 operator!=(basic_string_view<_CharT, _Traits> __x,
546 __type_identity_t<basic_string_view<_CharT, _Traits>> __y)
548 {
return !(__x == __y); }
550 template<
typename _CharT,
typename _Traits>
552 operator!=(__type_identity_t<basic_string_view<_CharT, _Traits>> __x,
553 basic_string_view<_CharT, _Traits> __y) noexcept
554 {
return !(__x == __y); }
556 template<
typename _CharT,
typename _Traits>
558 operator< (basic_string_view<_CharT, _Traits> __x,
559 basic_string_view<_CharT, _Traits> __y) noexcept
560 {
return __x.compare(__y) < 0; }
562 template<
typename _CharT,
typename _Traits>
564 operator< (basic_string_view<_CharT, _Traits> __x,
565 __type_identity_t<basic_string_view<_CharT, _Traits>> __y)
567 {
return __x.compare(__y) < 0; }
569 template<
typename _CharT,
typename _Traits>
571 operator< (__type_identity_t<basic_string_view<_CharT, _Traits>> __x,
572 basic_string_view<_CharT, _Traits> __y) noexcept
573 {
return __x.compare(__y) < 0; }
575 template<
typename _CharT,
typename _Traits>
577 operator> (basic_string_view<_CharT, _Traits> __x,
578 basic_string_view<_CharT, _Traits> __y) noexcept
579 {
return __x.compare(__y) > 0; }
581 template<
typename _CharT,
typename _Traits>
583 operator> (basic_string_view<_CharT, _Traits> __x,
584 __type_identity_t<basic_string_view<_CharT, _Traits>> __y)
586 {
return __x.compare(__y) > 0; }
588 template<
typename _CharT,
typename _Traits>
590 operator> (__type_identity_t<basic_string_view<_CharT, _Traits>> __x,
591 basic_string_view<_CharT, _Traits> __y) noexcept
592 {
return __x.compare(__y) > 0; }
594 template<
typename _CharT,
typename _Traits>
596 operator<=(basic_string_view<_CharT, _Traits> __x,
597 basic_string_view<_CharT, _Traits> __y) noexcept
598 {
return __x.compare(__y) <= 0; }
600 template<
typename _CharT,
typename _Traits>
602 operator<=(basic_string_view<_CharT, _Traits> __x,
603 __type_identity_t<basic_string_view<_CharT, _Traits>> __y)
605 {
return __x.compare(__y) <= 0; }
607 template<
typename _CharT,
typename _Traits>
609 operator<=(__type_identity_t<basic_string_view<_CharT, _Traits>> __x,
610 basic_string_view<_CharT, _Traits> __y) noexcept
611 {
return __x.compare(__y) <= 0; }
613 template<
typename _CharT,
typename _Traits>
615 operator>=(basic_string_view<_CharT, _Traits> __x,
616 basic_string_view<_CharT, _Traits> __y) noexcept
617 {
return __x.compare(__y) >= 0; }
619 template<
typename _CharT,
typename _Traits>
621 operator>=(basic_string_view<_CharT, _Traits> __x,
622 __type_identity_t<basic_string_view<_CharT, _Traits>> __y)
624 {
return __x.compare(__y) >= 0; }
626 template<
typename _CharT,
typename _Traits>
628 operator>=(__type_identity_t<basic_string_view<_CharT, _Traits>> __x,
629 basic_string_view<_CharT, _Traits> __y) noexcept
630 {
return __x.compare(__y) >= 0; }
634 template<
typename _CharT,
typename _Traits>
635 inline basic_ostream<_CharT, _Traits>&
636 operator<<(basic_ostream<_CharT, _Traits>& __os,
637 basic_string_view<_CharT,_Traits> __str)
638 {
return __ostream_insert(__os, __str.data(), __str.size()); }
643 using string_view = basic_string_view<char>;
644 #ifdef _GLIBCXX_USE_WCHAR_T
645 using wstring_view = basic_string_view<wchar_t>;
647 #ifdef _GLIBCXX_USE_CHAR8_T
648 using u8string_view = basic_string_view<char8_t>;
650 using u16string_view = basic_string_view<char16_t>;
651 using u32string_view = basic_string_view<char32_t>;
655 template<
typename _Tp>
659 struct hash<string_view>
660 :
public __hash_base<size_t, string_view>
663 operator()(
const string_view& __str)
const noexcept
664 {
return std::_Hash_impl::hash(__str.data(), __str.length()); }
671 #ifdef _GLIBCXX_USE_WCHAR_T
673 struct hash<wstring_view>
674 :
public __hash_base<size_t, wstring_view>
677 operator()(
const wstring_view& __s)
const noexcept
678 {
return std::_Hash_impl::hash(__s.data(),
679 __s.length() *
sizeof(
wchar_t)); }
687 #ifdef _GLIBCXX_USE_CHAR8_T
689 struct hash<u8string_view>
690 :
public __hash_base<size_t, u8string_view>
693 operator()(
const u8string_view& __str)
const noexcept
694 {
return std::_Hash_impl::hash(__str.data(), __str.length()); }
703 struct hash<u16string_view>
704 :
public __hash_base<size_t, u16string_view>
707 operator()(
const u16string_view& __s)
const noexcept
708 {
return std::_Hash_impl::hash(__s.data(),
709 __s.length() *
sizeof(char16_t)); }
717 struct hash<u32string_view>
718 :
public __hash_base<size_t, u32string_view>
721 operator()(
const u32string_view& __s)
const noexcept
722 {
return std::_Hash_impl::hash(__s.data(),
723 __s.length() *
sizeof(char32_t)); }
730 inline namespace literals
732 inline namespace string_view_literals
734 #pragma GCC diagnostic push
735 #pragma GCC diagnostic ignored "-Wliteral-suffix"
736 inline constexpr basic_string_view<char>
737 operator""sv(
const char* __str,
size_t __len) noexcept
738 {
return basic_string_view<char>{__str, __len}; }
740 #ifdef _GLIBCXX_USE_WCHAR_T
741 inline constexpr basic_string_view<wchar_t>
742 operator""sv(
const wchar_t* __str,
size_t __len) noexcept
743 {
return basic_string_view<wchar_t>{__str, __len}; }
746 #ifdef _GLIBCXX_USE_CHAR8_T
747 inline constexpr basic_string_view<char8_t>
748 operator""sv(
const char8_t* __str,
size_t __len) noexcept
749 {
return basic_string_view<char8_t>{__str, __len}; }
752 inline constexpr basic_string_view<char16_t>
753 operator""sv(
const char16_t* __str,
size_t __len) noexcept
754 {
return basic_string_view<char16_t>{__str, __len}; }
756 inline constexpr basic_string_view<char32_t>
757 operator""sv(
const char32_t* __str,
size_t __len) noexcept
758 {
return basic_string_view<char32_t>{__str, __len}; }
760 #pragma GCC diagnostic pop
764 #if __cpp_lib_concepts
768 template<
typename _CharT,
typename _Traits>
769 inline constexpr
bool
770 enable_borrowed_range<basic_string_view<_CharT, _Traits>> =
true;
773 template<
typename _CharT,
typename _Traits>
774 inline constexpr
bool
775 enable_view<basic_string_view<_CharT, _Traits>> =
true;
778 _GLIBCXX_END_NAMESPACE_VERSION
781 #include <bits/string_view.tcc>
constexpr const _Tp & min(const _Tp &, const _Tp &)
This does what you think it does.
ISO C++ entities toplevel namespace is std.
__numeric_traits_integer< _Tp > __int_traits
Convenience alias for __numeric_traits<integer-type>.
A non-owning reference to a string.