GCC Code Coverage Report


Directory: libs/url/
File: include/boost/url/grammar/string_view_base.hpp
Date: 2025-11-10 19:06:22
Exec Total Coverage
Lines: 54 54 100.0%
Functions: 60 60 100.0%
Branches: 0 0 -%

Line Branch Exec Source
1 //
2 // Copyright (c) 2022 Vinnie Falco (vinnie.falco@gmail.com)
3 //
4 // Distributed under the Boost Software License, Version 1.0. (See accompanying
5 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
6 //
7 // Official repository: https://github.com/boostorg/url
8 //
9
10 #ifndef BOOST_URL_GRAMMAR_STRING_VIEW_BASE_HPP
11 #define BOOST_URL_GRAMMAR_STRING_VIEW_BASE_HPP
12
13 #include <boost/url/detail/config.hpp>
14 #include <boost/url/detail/string_view.hpp>
15 #include <boost/core/detail/string_view.hpp>
16 #include <cstddef>
17 #include <iterator>
18 #include <string>
19 #include <type_traits>
20 #include <utility>
21
22 namespace boost {
23 namespace urls {
24 namespace grammar {
25
26 /** Common functionality for string views
27
28 This base class is used to provide common
29 member functions for reference types that
30 behave like string views. This cannot be
31 instantiated directly; instead, derive
32 from the type and provide constructors
33 which offer any desired preconditions
34 and invariants.
35 */
36 class string_view_base
37 {
38 protected:
39 /** The referenced character buffer
40 */
41 core::string_view s_;
42
43 /** Constructor
44
45 @param s The string view
46 */
47 constexpr
48 string_view_base(
49 core::string_view s) noexcept
50 : s_(s)
51 {
52 }
53
54 /** Constructor
55
56 @param data The character buffer
57 @param size The number of characters
58 */
59 constexpr
60 35047 string_view_base(
61 char const* data,
62 std::size_t size) noexcept
63 35047 : s_(data, size)
64 {
65 35047 }
66
67 /** Swap
68
69 @param s The object to swap with
70 */
71 // VFALCO No idea why this fails in msvc
72 /*BOOST_CXX14_CONSTEXPR*/
73 void
74 swap(
75 string_view_base& s ) noexcept
76 {
77 std::swap(s_, s.s_);
78 }
79
80 /** Constructor
81 */
82 16730 string_view_base() = default;
83
84 /** Constructor
85 */
86 string_view_base(
87 string_view_base const&) = default;
88
89 /** Assignment
90
91 @param other The object to assign
92 @return A reference to this object
93 */
94 string_view_base& operator=(
95 string_view_base const& other) = default;
96
97 public:
98 /// The character traits
99 typedef std::char_traits<char> traits_type;
100 /// The value type
101 typedef char value_type;
102 /// The pointer type
103 typedef char* pointer;
104 /// The const pointer type
105 typedef char const* const_pointer;
106 /// The reference type
107 typedef char& reference;
108 /// The const reference type
109 typedef char const& const_reference;
110 /// The const iterator type
111 typedef char const* const_iterator;
112 /// The iterator type
113 typedef const_iterator iterator;
114 /// The const reverse iterator type
115 typedef std::reverse_iterator<
116 const_iterator> const_reverse_iterator;
117 /// The reverse iterator type
118 typedef const_reverse_iterator reverse_iterator;
119 /// The size type
120 typedef std::size_t size_type;
121 /// The difference type
122 typedef std::ptrdiff_t difference_type;
123
124 /// A constant used to represent "no position"
125 static constexpr std::size_t npos = core::string_view::npos;
126
127 //--------------------------------------------
128
129 /** Conversion
130
131 @return A string view with the same contents
132 */
133 12059 operator
134 core::string_view() const noexcept
135 {
136 12059 return s_;
137 }
138
139 /** Conversion
140
141 @return A string view with the same contents
142 */
143 #if !defined(BOOST_NO_CXX17_HDR_STRING_VIEW)
144 operator
145 std::string_view() const noexcept
146 {
147 return std::string_view(s_);
148 }
149 #endif
150
151 /** Conversion
152
153 Conversion to std::string is explicit
154 because assigning to string using an
155 implicit constructor does not preserve
156 capacity.
157
158 @return A string with the same contents
159 */
160 explicit
161 47 operator
162 std::string() const noexcept
163 {
164 47 return std::string(s_);
165 }
166
167 //--------------------------------------------
168
169 // iterator support
170
171 /** Return an iterator to the beginning
172
173 See `core::string_view::begin`
174
175 @return An iterator to the beginning
176 */
177 359 BOOST_CONSTEXPR const_iterator begin() const noexcept
178 {
179 359 return s_.begin();
180 }
181
182 /** Return an iterator to the end
183
184 See `core::string_view::end`
185
186 @return An iterator to the end
187 */
188 359 BOOST_CONSTEXPR const_iterator end() const noexcept
189 {
190 359 return s_.end();
191 }
192
193 /** Return an iterator to the beginning
194
195 See `core::string_view::cbegin`
196
197 @return An iterator to the beginning
198 */
199 BOOST_CONSTEXPR const_iterator cbegin() const noexcept
200 {
201 return s_.cbegin();
202 }
203
204 /** Return an iterator to the end
205
206 See `core::string_view::cend`
207
208 @return An iterator to the end
209 */
210 BOOST_CONSTEXPR const_iterator cend() const noexcept
211 {
212 return s_.cend();
213 }
214
215 /** Return a reverse iterator to the end
216
217 See `core::string_view::rbegin`
218
219 @return A reverse iterator to the end
220 */
221 BOOST_URL_LIB_ARRAY_CONSTEXPR
222 const_reverse_iterator rbegin() const noexcept
223 {
224 return s_.rbegin();
225 }
226
227 /** Return a reverse iterator to the beginning
228
229 See `core::string_view::rend`
230
231 @return A reverse iterator to the beginning
232 */
233 BOOST_URL_LIB_ARRAY_CONSTEXPR
234 const_reverse_iterator rend() const noexcept
235 {
236 return s_.rend();
237 }
238
239 /** Return a reverse iterator to the end
240
241 See `core::string_view::crbegin`
242
243 @return A reverse iterator to the end
244 */
245 BOOST_URL_LIB_ARRAY_CONSTEXPR
246 const_reverse_iterator crbegin() const noexcept
247 {
248 return s_.crbegin();
249 }
250
251 /** Return a reverse iterator to the beginning
252
253 See `core::string_view::crend`
254
255 @return A reverse iterator to the beginning
256 */
257 BOOST_URL_LIB_ARRAY_CONSTEXPR
258 const_reverse_iterator crend() const noexcept
259 {
260 return s_.crend();
261 }
262
263 // capacity
264
265 /** Return the size
266
267 See `core::string_view::size`
268
269 @return The size
270 */
271 7265 BOOST_CONSTEXPR size_type size() const noexcept
272 {
273 7265 return s_.size();
274 }
275
276 /** Return the size
277
278 See `core::string_view::length`
279
280 @return The size
281 */
282 BOOST_CONSTEXPR size_type length() const noexcept
283 {
284 return s_.length();
285 }
286
287 /** Return the maximum allowed size
288
289 See `core::string_view::max_size`
290
291 @return The maximum allowed size
292 */
293 BOOST_CONSTEXPR size_type max_size() const noexcept
294 {
295 return s_.max_size();
296 }
297
298 /** Return true if the string is empty
299
300 See `core::string_view::size`
301
302 @return `true` if the string is empty
303 */
304 5022 BOOST_CONSTEXPR bool empty() const noexcept
305 {
306 5022 return s_.empty();
307 }
308
309 // element access
310
311 /** Access a character
312
313 See `core::string_view::operator[]`
314
315 @param pos The position to access
316 @return The character at the position
317 */
318 BOOST_CXX14_CONSTEXPR const_reference
319 25 operator[]( size_type pos ) const noexcept
320 {
321 25 return s_[pos];
322 }
323
324 /** Access a character
325
326 See `core::string_view::at`
327
328 @param pos The position to access
329 @return The character at the position
330 */
331 BOOST_CXX14_CONSTEXPR const_reference
332 at( size_type pos ) const
333 {
334 return s_.at(pos);
335 }
336
337 /** Return the first character
338
339 See `core::string_view::front`
340
341 @return The first character
342 */
343 BOOST_CXX14_CONSTEXPR const_reference
344 80 front() const noexcept
345 {
346 80 return s_.front();
347 }
348
349 /** Return the last character
350
351 See `core::string_view::back`
352
353 @return The last character
354 */
355 BOOST_CXX14_CONSTEXPR const_reference
356 17 back() const noexcept
357 {
358 17 return s_.back();
359 }
360
361 /** Return a pointer to the character buffer
362
363 See `core::string_view::data`
364
365 @return A pointer to the character buffer
366 */
367 BOOST_CONSTEXPR const_pointer
368 692 data() const noexcept
369 {
370 692 return s_.data();
371 }
372
373 // string operations
374
375 /** Copy the characters to another buffer
376
377 See `core::string_view::copy`
378
379 @param s The destination buffer
380 @param n The number of characters to copy
381 @param pos The position to start from
382 @return The number of characters copied
383 */
384 BOOST_CXX14_CONSTEXPR size_type copy(
385 char* s, size_type n, size_type pos = 0 ) const
386 {
387 return s_.copy(s, n, pos);
388 }
389
390 /** Return a view to part of the string
391
392 See `core::string_view::substr`
393
394 @param pos The position to start from
395 @param n The number of characters
396 @return A view to the substring
397 */
398 10134 BOOST_CXX14_CONSTEXPR core::string_view substr(
399 size_type pos = 0, size_type n = core::string_view::npos ) const
400 {
401 10134 return s_.substr(pos, n);
402 }
403
404 // comparison
405
406 /** Return the result of comparing to another string
407
408 See `core::string_view::compare`
409
410 @param str The string to compare
411 @return The result of the comparison
412 */
413 BOOST_CXX14_CONSTEXPR int
414 compare( core::string_view str ) const noexcept
415 {
416 return s_.compare(str);
417 }
418
419 /** Return the result of comparing to another string
420
421 See `core::string_view::compare`
422
423 @param pos1 The position to start comparing from
424 @param n1 The number of characters to compare
425 @param str The string to compare
426 @return The result of the comparison
427 */
428 BOOST_CONSTEXPR int compare(
429 size_type pos1, size_type n1, core::string_view str ) const
430 {
431 return s_.compare(pos1, n1, str);
432 }
433
434 /** Return the result of comparing to another string
435
436 See `core::string_view::compare`
437
438 @param pos1 The position to start comparing from
439 @param n1 The number of characters to compare
440 @param str The string to compare
441 @param pos2 The position to start comparing from
442 @param n2 The number of characters to compare
443 @return The result of the comparison
444 */
445 BOOST_CONSTEXPR int compare(
446 size_type pos1, size_type n1, core::string_view str,
447 size_type pos2, size_type n2 ) const
448 {
449 return s_.compare(pos1, n1, str, pos2, n2);
450 }
451
452 /** Return the result of comparing to another string
453
454 See `core::string_view::compare`
455
456 @param s The string to compare
457 @return The result of the comparison
458 */
459 BOOST_CONSTEXPR int compare(
460 char const* s ) const noexcept
461 {
462 return s_.compare(s);
463 }
464
465 /** Return the result of comparing to another string
466
467 See `core::string_view::compare`
468
469 @param pos1 The position to start comparing from
470 @param n1 The number of characters to compare
471 @param s The string to compare
472 @return The result of the comparison
473 */
474 BOOST_CONSTEXPR int compare(
475 size_type pos1, size_type n1, char const* s ) const
476 {
477 return s_.compare(pos1, n1, s);
478 }
479
480 /** Return the result of comparing to another string
481
482 See `core::string_view::compare`
483
484 @param pos1 The position to start comparing from
485 @param n1 The number of characters to compare
486 @param s The string to compare
487 @param n2 The number of characters to compare
488 @return The result of the comparison
489 */
490 BOOST_CONSTEXPR int compare(
491 size_type pos1, size_type n1,
492 char const* s, size_type n2 ) const
493 {
494 return s_.compare(pos1, n1, s, n2);
495 }
496
497 // starts_with
498
499 /** Return true if a matching prefix exists
500
501 See `core::string_view::starts_with`
502
503 @param x The string to search for
504 @return `true` if the prefix matches
505 */
506 BOOST_CONSTEXPR bool starts_with(
507 core::string_view x ) const noexcept
508 {
509 return s_.starts_with(x);
510 }
511
512 /** Return true if a matching prefix exists
513
514 See `core::string_view::starts_with`
515
516 @param x The character to search for
517 @return `true` if the prefix matches
518 */
519 602 BOOST_CONSTEXPR bool starts_with(
520 char x ) const noexcept
521 {
522 602 return s_.starts_with(x);
523 }
524
525 /** Return true if a matching prefix exists
526
527 See `core::string_view::starts_with`
528
529 @param x The string to search for
530 @return `true` if the prefix matches
531 */
532 235 BOOST_CONSTEXPR bool starts_with(
533 char const* x ) const noexcept
534 {
535 235 return s_.starts_with(x);
536 }
537
538 // ends_with
539
540 /** Return true if a matching suffix exists
541
542 See `core::string_view::ends_with`
543
544 @param x The string to search for
545 @return `true` if the suffix matches
546 */
547 BOOST_CONSTEXPR bool ends_with(
548 core::string_view x ) const noexcept
549 {
550 return s_.ends_with(x);
551 }
552
553 /** Return true if a matching suffix exists
554
555 See `core::string_view::ends_with`
556
557 @param x The character to search for
558 @return `true` if the suffix matches
559 */
560 549 BOOST_CONSTEXPR bool ends_with(
561 char x ) const noexcept
562 {
563 549 return s_.ends_with(x);
564 }
565
566 /** Return true if a matching suffix exists
567
568 See `core::string_view::ends_with`
569
570 @param x The string to search for
571 @return `true` if the suffix matches
572 */
573 BOOST_CONSTEXPR bool ends_with(
574 char const* x ) const noexcept
575 {
576 return s_.ends_with(x);
577 }
578
579 // find
580
581 /** Return the position of matching characters
582
583 See `core::string_view::find`
584
585 @param str The characters to search for
586 @param pos The position to start searching from
587 @return The position of the first match
588 */
589 BOOST_CONSTEXPR size_type find(
590 core::string_view str, size_type pos = 0 ) const noexcept
591 {
592 return s_.find(str, pos);
593 }
594
595 /** Return the position of matching characters
596
597 See `core::string_view::find`
598
599 @param c The character to search for
600 @param pos The position to start searching from
601 @return The position of the first match
602 */
603 10 BOOST_CXX14_CONSTEXPR size_type find(
604 char c, size_type pos = 0 ) const noexcept
605 {
606 10 return s_.find(c, pos);
607 }
608
609 /** Return the position of matching characters
610
611 See `core::string_view::find`
612
613 @param s The characters to search for
614 @param pos The position to start searching from
615 @param n The number of characters to search for
616 @return The position of the first match
617 */
618 BOOST_CXX14_CONSTEXPR size_type find(
619 char const* s, size_type pos, size_type n ) const noexcept
620 {
621 return s_.find(s, pos, n);
622 }
623
624 /** Return the position of matching characters
625
626 See `core::string_view::find`
627
628 @param s The characters to search for
629 @param pos The position to start searching from
630 @return The position of the first match
631 */
632 BOOST_CONSTEXPR size_type find(
633 char const* s, size_type pos = 0 ) const noexcept
634 {
635 return s_.find(s, pos);
636 }
637
638 // rfind
639
640 /** Return the position of matching characters
641
642 See `core::string_view::rfind`
643
644 @param str The characters to search for
645 @param pos The position to start searching from
646 @return The position of the first match
647 */
648 BOOST_CONSTEXPR size_type rfind(
649 core::string_view str, size_type pos = core::string_view::npos ) const noexcept
650 {
651 return s_.rfind(str, pos);
652 }
653
654 /** Return the position of matching characters
655
656 See `core::string_view::rfind`
657
658 @param c The character to search for
659 @param pos The position to start searching from
660 @return The position of the first match
661 */
662 BOOST_CXX14_CONSTEXPR size_type rfind(
663 char c, size_type pos = core::string_view::npos ) const noexcept
664 {
665 return s_.rfind(c, pos);
666 }
667
668 /** Return the position of matching characters
669
670 See `core::string_view::rfind`
671
672 @param s The characters to search for
673 @param pos The position to start searching from
674 @param n The number of characters to search for
675 @return The position of the first match
676 */
677 BOOST_CXX14_CONSTEXPR size_type rfind(
678 char const* s, size_type pos, size_type n ) const noexcept
679 {
680 return s_.rfind(s, pos, n);
681 }
682
683 /** Return the position of matching characters
684
685 See `core::string_view::rfind`
686
687 @param s The characters to search for
688 @param pos The position to start searching from
689 @return The position of the first match
690 */
691 BOOST_CONSTEXPR size_type rfind(
692 char const* s, size_type pos = core::string_view::npos ) const noexcept
693 {
694 return s_.rfind(s, pos);
695 }
696
697 // find_first_of
698
699 /** Return the position of the first match
700
701 See `core::string_view::find_first_of`
702
703 @param str The characters to search for
704 @param pos The position to start searching from
705 @return The position of the first match
706 */
707 BOOST_CXX14_CONSTEXPR size_type find_first_of(
708 core::string_view str, size_type pos = 0 ) const noexcept
709 {
710 return s_.find_first_of(str, pos);
711 }
712
713 /** Return the position of the first match
714
715 See `core::string_view::find_first_of`
716
717 @param c The character to search for
718 @param pos The position to start searching from
719 @return The position of the first match
720 */
721 52 BOOST_CONSTEXPR size_type find_first_of(
722 char c, size_type pos = 0 ) const noexcept
723 {
724 52 return s_.find_first_of(c, pos);
725 }
726
727 /** Return the position of the first match
728
729 See `core::string_view::find_first_of`
730
731 @param s The characters to search for
732 @param pos The position to start searching from
733 @param n The number of characters to search for
734 @return The position of the first match
735 */
736 BOOST_CXX14_CONSTEXPR size_type find_first_of(
737 char const* s, size_type pos, size_type n ) const noexcept
738 {
739 return s_.find_first_of(s, pos, n);
740 }
741
742 /** Return the position of the first match
743
744 See `core::string_view::find_first_of`
745
746 @param s The characters to search for
747 @param pos The position to start searching from
748 @return The position of the first match
749 */
750 5 BOOST_CXX14_CONSTEXPR size_type find_first_of(
751 char const* s, size_type pos = 0 ) const noexcept
752 {
753 5 return s_.find_first_of(s, pos);
754 }
755
756 // find_last_of
757
758 /** Return the position of the last match
759
760 See `core::string_view::find_last_of`
761
762 @param str The characters to search for
763 @param pos The position to start searching from
764 @return The position of the last match
765 */
766 BOOST_CXX14_CONSTEXPR size_type find_last_of(
767 core::string_view str, size_type pos = core::string_view::npos ) const noexcept
768 {
769 return s_.find_last_of(str, pos);
770 }
771
772 /** Return the position of the last match
773
774 See `core::string_view::find_last_of`
775
776 @param c The character to search for
777 @param pos The position to start searching from
778 @return The position of the last match
779 */
780 BOOST_CONSTEXPR size_type find_last_of(
781 char c, size_type pos = core::string_view::npos ) const noexcept
782 {
783 return s_.find_last_of(c, pos);
784 }
785
786 /** Return the position of the last match
787
788 See `core::string_view::find_last_of`
789
790 @param s The characters to search for
791 @param pos The position to start searching from
792 @param n The number of characters to search for
793 @return The position of the last match
794 */
795 BOOST_CXX14_CONSTEXPR size_type find_last_of(
796 char const* s, size_type pos, size_type n ) const noexcept
797 {
798 return s_.find_last_of(s, pos, n);
799 }
800
801 /** Return the position of the last match
802
803 See `core::string_view::find_last_of`
804
805 @param s The characters to search for
806 @param pos The position to start searching from
807 @return The position of the last match
808 */
809 BOOST_CXX14_CONSTEXPR size_type find_last_of(
810 char const* s, size_type pos = core::string_view::npos ) const noexcept
811 {
812 return s_.find_last_of(s, pos);
813 }
814
815 // find_first_not_of
816
817 /** Return the position of the first non-match
818
819 See `core::string_view::find_first_not_of`
820
821 @param str The characters to search for
822 @param pos The position to start searching from
823 @return The position of the first non-match
824 */
825 BOOST_CXX14_CONSTEXPR size_type find_first_not_of(
826 core::string_view str, size_type pos = 0 ) const noexcept
827 {
828 return s_.find_first_not_of(str, pos);
829 }
830
831 /** Return the position of the first non-match
832
833 See `core::string_view::find_first_not_of`
834
835 @param c The character to search for
836 @param pos The position to start searching from
837 @return The position of the first non-match
838 */
839 BOOST_CXX14_CONSTEXPR size_type find_first_not_of(
840 char c, size_type pos = 0 ) const noexcept
841 {
842 return s_.find_first_not_of(c, pos);
843 }
844
845 /** Return the position of the first non-match
846
847 See `core::string_view::find_first_not_of`
848
849 @param s The characters to search for
850 @param pos The position to start searching from
851 @param n The number of characters to search for
852 @return The position of the first non-match
853 */
854 BOOST_CXX14_CONSTEXPR size_type find_first_not_of(
855 char const* s, size_type pos, size_type n ) const noexcept
856 {
857 return s_.find_first_not_of(s, pos, n);
858 }
859
860 /** Return the position of the first non-match
861
862 See `core::string_view::find_first_not_of`
863
864 @param s The characters to search for
865 @param pos The position to start searching from
866 @return The position of the first non-match
867 */
868 BOOST_CXX14_CONSTEXPR size_type find_first_not_of(
869 char const* s, size_type pos = 0 ) const noexcept
870 {
871 return s_.find_first_not_of(s, pos);
872 }
873
874 // find_last_not_of
875
876 /** Return the position of the last non-match
877
878 See `core::string_view::find_last_not_of`
879
880 @param str The characters to search for
881 @param pos The position to start searching from
882 @return The position of the last non-match
883 */
884 BOOST_CXX14_CONSTEXPR size_type find_last_not_of(
885 core::string_view str, size_type pos = core::string_view::npos ) const noexcept
886 {
887 return s_.find_last_not_of(str, pos);
888 }
889
890 /** Return the position of the last non-match
891
892 See `core::string_view::find_last_not_of`
893
894 @param c The character to search for
895 @param pos The position to start searching from
896 @return The position of the last non-match
897 */
898 BOOST_CXX14_CONSTEXPR size_type find_last_not_of(
899 char c, size_type pos = core::string_view::npos ) const noexcept
900 {
901 return s_.find_last_not_of(c, pos);
902 }
903
904 /** Return the position of the last non-match
905
906 See `core::string_view::find_last_not_of`
907
908 @param s The characters to search for
909 @param pos The position to start searching from
910 @param n The number of characters to search for
911 @return The position of the last non-match
912 */
913 BOOST_CXX14_CONSTEXPR size_type find_last_not_of(
914 char const* s, size_type pos, size_type n ) const noexcept
915 {
916 return s_.find_last_not_of(s, pos, n);
917 }
918
919 /** Return the position of the last non-match
920
921 See `core::string_view::find_last_not_of`
922
923 @param s The characters to search for
924 @param pos The position to start searching from
925 @return The position of the last non-match
926 */
927 BOOST_CXX14_CONSTEXPR size_type find_last_not_of(
928 char const* s, size_type pos = core::string_view::npos ) const noexcept
929 {
930 return s_.find_last_not_of(s, pos);
931 }
932
933 // contains
934
935 /** Return true if matching characters are found
936
937 See `core::string_view::contains`
938
939 @param sv The string to search for
940 @return `true` if the string contains the characters, otherwise `false`
941 */
942 BOOST_CONSTEXPR bool contains( core::string_view sv ) const noexcept
943 {
944 return s_.contains(sv);
945 }
946
947 /** Return true if matching characters are found
948
949 See `core::string_view::contains`
950
951 @param c The character to search for
952 @return `true` if the string contains the character, otherwise `false`
953 */
954 5 BOOST_CXX14_CONSTEXPR bool contains( char c ) const noexcept
955 {
956 5 return s_.contains(c);
957 }
958
959 /** Return true if matching characters are found
960
961 See `core::string_view::contains`
962
963 @param s The string to search for
964 @return `true` if the string contains the characters, otherwise `false`
965 */
966 BOOST_CONSTEXPR bool contains( char const* s ) const noexcept
967 {
968 return s_.contains(s);
969 }
970
971 // relational operators
972 #ifndef BOOST_URL_DOCS
973 private:
974 template<class S0, class S1>
975 using is_match = std::integral_constant<bool,
976 std::is_convertible<S0, core::string_view>::value &&
977 std::is_convertible<S1, core::string_view>::value && (
978 (std::is_base_of<string_view_base,
979 typename std::decay<S0>::type>::value &&
980 std::is_convertible<S0 const volatile*,
981 string_view_base const volatile*>::value) ||
982 (std::is_base_of<string_view_base,
983 typename std::decay<S1>::type>::value &&
984 std::is_convertible<S1 const volatile*,
985 string_view_base const volatile*>::value))>;
986 public:
987
988 /** Compare two string views for equality
989
990 This function is only enabled if both arguments
991 are convertible to `core::string_view` and at least
992 one of the arguments is derived from `string_view_base`.
993
994 @param s0 The first string
995 @param s1 The second string
996 @return `true` if the strings are equal, otherwise `false`
997 */
998 template<class S0, class S1>
999 3062 BOOST_CXX14_CONSTEXPR friend auto operator==(
1000 S0 const& s0, S1 const& s1) noexcept ->
1001 typename std::enable_if<
1002 is_match<S0, S1>::value, bool>::type
1003 {
1004 3062 return urls::detail::to_sv(s0) == urls::detail::to_sv(s1);
1005 }
1006
1007 /** Compare two string views for inequality
1008
1009 This function is only enabled if both arguments
1010 are convertible to `core::string_view` and at least
1011 one of the arguments is derived from `string_view_base`.
1012
1013 @param s0 The first string
1014 @param s1 The second string
1015 @return `true` if the strings are not equal, otherwise `false`
1016 */
1017 template<class S0, class S1>
1018 80 BOOST_CXX14_CONSTEXPR friend auto operator!=(
1019 S0 const& s0, S1 const& s1) noexcept ->
1020 typename std::enable_if<
1021 is_match<S0, S1>::value, bool>::type
1022 {
1023 80 return urls::detail::to_sv(s0) != urls::detail::to_sv(s1);
1024 }
1025
1026 /** Compare two string views for less than
1027
1028 This function is only enabled if both arguments
1029 are convertible to `core::string_view` and at least
1030 one of the arguments is derived from `string_view_base`.
1031
1032 @param s0 The first string
1033 @param s1 The second string
1034 @return `true` if the first string is less than the second, otherwise `false`
1035 */
1036 template<class S0, class S1>
1037 14 BOOST_CXX14_CONSTEXPR friend auto operator<(
1038 S0 const& s0, S1 const& s1) noexcept ->
1039 typename std::enable_if<
1040 is_match<S0, S1>::value, bool>::type
1041 {
1042 14 return urls::detail::to_sv(s0) < urls::detail::to_sv(s1);
1043 }
1044
1045 /** Compare two string views for less than or equal
1046
1047 This function is only enabled if both arguments
1048 are convertible to `core::string_view` and at least
1049 one of the arguments is derived from `string_view_base`.
1050
1051 @param s0 The first string
1052 @param s1 The second string
1053 @return `true` if the first string is less than or equal to the second, otherwise `false`
1054 */
1055 template<class S0, class S1>
1056 14 BOOST_CXX14_CONSTEXPR friend auto operator<=(
1057 S0 const& s0, S1 const& s1) noexcept ->
1058 typename std::enable_if<
1059 is_match<S0, S1>::value, bool>::type
1060 {
1061 14 return urls::detail::to_sv(s0) <= urls::detail::to_sv(s1);
1062 }
1063
1064 /** Compare two string views for greater than
1065
1066 This function is only enabled if both arguments
1067 are convertible to `core::string_view` and at least
1068 one of the arguments is derived from `string_view_base`.
1069
1070 @param s0 The first string
1071 @param s1 The second string
1072 @return `true` if the first string is greater than the second, otherwise `false`
1073 */
1074 template<class S0, class S1>
1075 14 BOOST_CXX14_CONSTEXPR friend auto operator>(
1076 S0 const& s0, S1 const& s1) noexcept ->
1077 typename std::enable_if<
1078 is_match<S0, S1>::value, bool>::type
1079 {
1080 14 return urls::detail::to_sv(s0) > urls::detail::to_sv(s1);
1081 }
1082
1083 /** Compare two string views for greater than or equal
1084
1085 This function is only enabled if both arguments
1086 are convertible to `core::string_view` and at least
1087 one of the arguments is derived from `string_view_base`.
1088
1089 @param s0 The first string
1090 @param s1 The second string
1091 @return `true` if the first string is greater than or equal to the second, otherwise `false`
1092 */
1093 template<class S0, class S1>
1094 7 BOOST_CXX14_CONSTEXPR friend auto operator>=(
1095 S0 const& s0, S1 const& s1) noexcept ->
1096 typename std::enable_if<
1097 is_match<S0, S1>::value, bool>::type
1098 {
1099 7 return urls::detail::to_sv(s0) >= urls::detail::to_sv(s1);
1100 }
1101 #endif
1102
1103 //--------------------------------------------
1104
1105 /** Format a string to an output stream
1106
1107 @param os The output stream to write to
1108 @param s The string to write
1109 @return A reference to the output stream, for chaining
1110 */
1111 BOOST_URL_DECL
1112 friend
1113 std::ostream&
1114 operator<<(
1115 std::ostream& os,
1116 string_view_base const& s);
1117 };
1118
1119 //------------------------------------------------
1120
1121 /** Format a string to an output stream
1122 */
1123 BOOST_URL_DECL
1124 std::ostream&
1125 operator<<(
1126 std::ostream& os,
1127 string_view_base const& s);
1128
1129 } // grammar
1130
1131 #ifndef BOOST_URL_DOCS
1132 namespace detail {
1133 template <>
1134 inline
1135 core::string_view
1136 32 to_sv(grammar::string_view_base const& s) noexcept
1137 {
1138 32 return s.operator core::string_view();
1139 }
1140 } // detail
1141 #endif
1142
1143 } // urls
1144 } // boost
1145
1146 #endif
1147