1/*
2 *
3 * Copyright 2015 gRPC authors.
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 */
18
19#ifndef GRPCPP_IMPL_CODEGEN_STRING_REF_H
20#define GRPCPP_IMPL_CODEGEN_STRING_REF_H
21
22#include <string.h>
23
24#include <algorithm>
25#include <iosfwd>
26#include <iostream>
27#include <iterator>
28
29#include <grpcpp/impl/codegen/config.h>
30
31namespace grpc {
32
33/// This class is a non owning reference to a string.
34///
35/// It should be a strict subset of the upcoming std::string_ref.
36///
37/// \see http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3442.html
38///
39/// The constexpr is dropped or replaced with const for legacy compiler
40/// compatibility.
41class string_ref {
42 public:
43 /// types
44 typedef const char* const_iterator;
45 typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
46
47 /// constants
48 const static size_t npos;
49
50 /// construct/copy.
51 string_ref() : data_(nullptr), length_(0) {}
52 string_ref(const string_ref& other)
53 : data_(other.data_), length_(other.length_) {}
54 string_ref& operator=(const string_ref& rhs) {
55 data_ = rhs.data_;
56 length_ = rhs.length_;
57 return *this;
58 }
59
60 string_ref(const char* s) : data_(s), length_(strlen(s: s)) {}
61 string_ref(const char* s, size_t l) : data_(s), length_(l) {}
62 string_ref(const grpc::string& s) : data_(s.data()), length_(s.length()) {}
63
64 /// iterators
65 const_iterator begin() const { return data_; }
66 const_iterator end() const { return data_ + length_; }
67 const_iterator cbegin() const { return data_; }
68 const_iterator cend() const { return data_ + length_; }
69 const_reverse_iterator rbegin() const {
70 return const_reverse_iterator(end());
71 }
72 const_reverse_iterator rend() const {
73 return const_reverse_iterator(begin());
74 }
75 const_reverse_iterator crbegin() const {
76 return const_reverse_iterator(end());
77 }
78 const_reverse_iterator crend() const {
79 return const_reverse_iterator(begin());
80 }
81
82 /// capacity
83 size_t size() const { return length_; }
84 size_t length() const { return length_; }
85 size_t max_size() const { return length_; }
86 bool empty() const { return length_ == 0; }
87
88 /// element access
89 const char* data() const { return data_; }
90
91 /// string operations
92 int compare(string_ref x) const {
93 size_t min_size = length_ < x.length_ ? length_ : x.length_;
94 int r = memcmp(s1: data_, s2: x.data_, n: min_size);
95 if (r < 0) return -1;
96 if (r > 0) return 1;
97 if (length_ < x.length_) return -1;
98 if (length_ > x.length_) return 1;
99 return 0;
100 }
101
102 bool starts_with(string_ref x) const {
103 return length_ >= x.length_ && (memcmp(s1: data_, s2: x.data_, n: x.length_) == 0);
104 }
105
106 bool ends_with(string_ref x) const {
107 return length_ >= x.length_ &&
108 (memcmp(s1: data_ + (length_ - x.length_), s2: x.data_, n: x.length_) == 0);
109 }
110
111 size_t find(string_ref s) const {
112 auto it = std::search(first1: cbegin(), last1: cend(), first2: s.cbegin(), last2: s.cend());
113 return it == cend() ? npos : std::distance(first: cbegin(), last: it);
114 }
115
116 size_t find(char c) const {
117 auto it = std::find(first: cbegin(), last: cend(), val: c);
118 return it == cend() ? npos : std::distance(first: cbegin(), last: it);
119 }
120
121 string_ref substr(size_t pos, size_t n = npos) const {
122 if (pos > length_) pos = length_;
123 if (n > (length_ - pos)) n = length_ - pos;
124 return string_ref(data_ + pos, n);
125 }
126
127 private:
128 const char* data_;
129 size_t length_;
130};
131
132/// Comparison operators
133inline bool operator==(string_ref x, string_ref y) { return x.compare(x: y) == 0; }
134inline bool operator!=(string_ref x, string_ref y) { return x.compare(x: y) != 0; }
135inline bool operator<(string_ref x, string_ref y) { return x.compare(x: y) < 0; }
136inline bool operator<=(string_ref x, string_ref y) { return x.compare(x: y) <= 0; }
137inline bool operator>(string_ref x, string_ref y) { return x.compare(x: y) > 0; }
138inline bool operator>=(string_ref x, string_ref y) { return x.compare(x: y) >= 0; }
139
140inline std::ostream& operator<<(std::ostream& out, const string_ref& string) {
141 return out << grpc::string(string.begin(), string.end());
142}
143
144} // namespace grpc
145
146#endif // GRPCPP_IMPL_CODEGEN_STRING_REF_H
147

source code of include/grpcpp/impl/codegen/string_ref.h