userver
C++ Async Framework
Loading...
Searching...
No Matches
small_string.hpp
Go to the documentation of this file.
1
#
pragma
once
2
3
/// @file userver/utils/small_string.hpp
4
/// @brief @copybrief utils::SmallString
5
6
#
include
<
cstddef
>
7
#
include
<
functional
>
8
#
include
<
stdexcept
>
9
#
include
<
string
>
10
11
#
include
<
boost
/
container
/
small_vector
.
hpp
>
12
13
#
include
<
userver
/
utils
/
assert
.
hpp
>
14
15
USERVER_NAMESPACE_BEGIN
16
17
namespace
utils
{
18
19
/// @ingroup userver_universal userver_containers
20
///
21
/// @brief An alternative to std::string with a custom SSO (small string
22
/// optimization) container size. Unlike std::string, SmallString is not
23
/// null-terminated thus it has no c_str(), data() returns a not null-terminated
24
/// buffer.
25
template
<std::size_t N>
26
class
SmallString
final {
27
using
Container
=
boost
::
container
::
small_vector
<
char
,
N
>;
28
29
public
:
30
/// @brief Create empty string.
31
SmallString
() =
default
;
32
33
/// @brief Create a string from another one.
34
SmallString
(
const
SmallString
<N>&) =
default
;
35
36
/// @brief Create a string from another one.
37
explicit
SmallString
(
SmallString
<N>&&)
noexcept
=
default
;
38
39
/// @brief Create a string from std::string_view.
40
explicit
SmallString
(std::string_view sv);
41
42
/// @brief Assign the value of other string_view to this string.
43
SmallString
&
operator
=(std::string_view sv);
44
45
/// @brief Assign the value of other string to this string.
46
SmallString
&
operator
=(
const
SmallString
&) =
default
;
47
48
/// @brief Assign the value of other string to this string.
49
SmallString
&
operator
=(
SmallString
&&)
noexcept
=
default
;
50
51
/// @brief Convert string to a std::string_view.
52
operator
std
::
string_view
()
const
;
53
54
/// @brief Read-only subscript access to the data contained in the string.
55
const
char
&
operator
[](std::size_t pos)
const
;
56
57
/// @brief Subscript access to the data contained in the string.
58
char
&
operator
[](std::size_t pos);
59
60
/// @brief Provides access to the data contained in the string.
61
const
char
&
at
(std::size_t pos)
const
;
62
63
/// @brief Provides access to the data contained in the string.
64
char
&
at
(std::size_t pos);
65
66
using
iterator
=
typename
Container
::
iterator
;
67
68
using
const_iterator
=
typename
Container
::
const_iterator
;
69
70
iterator begin()
noexcept
;
71
const_iterator begin()
const
noexcept
;
72
73
iterator end()
noexcept
;
74
const_iterator end()
const
noexcept
;
75
76
/// @brief Get string size.
77
std::size_t
size
()
const
noexcept
;
78
79
/// @brief Get pointer to data.
80
/// @warning The buffer is not null-terminated.
81
const
char
*
data
()
const
noexcept
;
82
83
/// @brief Get pointer to data.
84
/// @warning The buffer is not null-terminated.
85
char
*
data
()
noexcept
;
86
87
/// @brief Resize the string. If its length is increased,
88
/// fill new chars with %c.
89
void
resize
(std::size_t n,
char
c);
90
91
/// @brief Resize the string. Use op to write into the string and replace a
92
/// sequence of characters
93
template
<
class
Operation>
94
void
resize_and_overwrite
(std::size_t size, Operation op);
95
96
/// @brief Shrink the string's size to fit all contents
97
void
shrink_to_fit
();
98
99
/// @brief Get current capacity.
100
std::size_t
capacity
()
const
noexcept
;
101
102
/// @brief Reserve to %n bytes.
103
void
reserve
(std::size_t n);
104
105
/// @brief Clear the string.
106
void
clear
()
noexcept
;
107
108
/// @brief Is the string empty?
109
bool
empty
()
const
noexcept
;
110
111
/// @brief Get a reference to the first character.
112
char
&
front
();
113
114
/// @brief Get a reference to the first character.
115
const
char
&
front
()
const
;
116
117
/// @brief Get a reference to the last character.
118
char
&
back
();
119
120
/// @brief Get a reference to the last character.
121
const
char
&
back
()
const
;
122
123
/// @brief Append a character to the string.
124
void
push_back
(
char
c);
125
126
/// @brief Append contents of a string_view to the string.
127
void
append
(std::string_view str);
128
129
/// @brief Remove the last character from the string.
130
void
pop_back
();
131
132
private
:
133
boost::container::small_vector<
char
, N> data_;
134
};
135
136
template
<std::size_t N>
137
SmallString
<N>::
SmallString
(std::string_view sv) :
data_
(
sv
.
begin
(),
sv
.
end
()) {}
138
139
template
<
std
::
size_t
N
>
140
SmallString
<
N
>::
operator
std
::
string_view
()
const
{
141
return
std
::
string_view
{
data_
.
data
(),
data_
.
size
()};
142
}
143
144
template
<
std
::
size_t
N
>
145
SmallString
<
N
>&
SmallString
<
N
>::
operator
=(
std
::
string_view
sv
) {
146
data_
= {
sv
.
begin
(),
sv
.
end
()};
147
return
*
this
;
148
}
149
150
template
<
std
::
size_t
N
>
151
bool
operator
==(
const
SmallString
<
N
>&
str
,
std
::
string_view
sv
) {
152
return
std
::
string_view
{
str
} ==
sv
;
153
}
154
155
template
<
std
::
size_t
N
>
156
bool
operator
==(
std
::
string_view
sv
,
const
SmallString
<
N
>&
str
) {
157
return
std
::
string_view
{
str
} ==
sv
;
158
}
159
160
template
<
std
::
size_t
N
>
161
bool
operator
==(
const
SmallString
<
N
>&
str1
,
const
SmallString
<
N
>&
str2
) {
162
return
std
::
string_view
{
str1
} ==
std
::
string_view
{
str2
};
163
}
164
165
template
<
std
::
size_t
N
>
166
bool
operator
!=(
const
SmallString
<
N
>&
str1
,
const
SmallString
<
N
>&
str2
) {
167
return
!(
str1
==
str2
);
168
}
169
170
template
<
std
::
size_t
N
>
171
const
char
&
SmallString
<
N
>::
operator
[](
std
::
size_t
pos
)
const
{
172
return
data_
[
pos
];
173
}
174
175
template
<
std
::
size_t
N
>
176
char
&
SmallString
<
N
>::
operator
[](
std
::
size_t
pos
) {
177
return
data_
[
pos
];
178
}
179
180
template
<
std
::
size_t
N
>
181
const
char
&
SmallString
<
N
>::
at
(
std
::
size_t
pos
)
const
{
182
if
(
size
() <=
pos
)
throw
std
::
out_of_range
(
"at"
);
183
return
data_
[
pos
];
184
}
185
186
template
<
std
::
size_t
N
>
187
char
&
SmallString
<
N
>::
at
(
std
::
size_t
pos
) {
188
if
(
size
() <=
pos
)
throw
std
::
out_of_range
(
"at"
);
189
return
data_
[
pos
];
190
}
191
192
template
<
std
::
size_t
N
>
193
typename
SmallString
<
N
>::
iterator
SmallString
<
N
>::
begin
()
noexcept
{
194
return
{
data_
.
begin
()};
195
}
196
197
template
<
std
::
size_t
N
>
198
typename
SmallString
<
N
>::
const_iterator
SmallString
<
N
>::
begin
()
const
noexcept
{
199
return
{
data_
.
begin
()};
200
}
201
202
template
<
std
::
size_t
N
>
203
typename
SmallString
<
N
>::
iterator
SmallString
<
N
>::
end
()
noexcept
{
204
return
{
data_
.
end
()};
205
}
206
207
template
<
std
::
size_t
N
>
208
typename
SmallString
<
N
>::
const_iterator
SmallString
<
N
>::
end
()
const
noexcept
{
209
return
{
data_
.
end
()};
210
}
211
212
template
<
std
::
size_t
N
>
213
std
::
size_t
SmallString
<
N
>::
size
()
const
noexcept
{
214
return
data_
.
size
();
215
}
216
217
template
<
std
::
size_t
N
>
218
const
char
*
SmallString
<
N
>::
data
()
const
noexcept
{
219
return
data_
.
data
();
220
}
221
222
template
<
std
::
size_t
N
>
223
char
*
SmallString
<
N
>::
data
()
noexcept
{
224
return
data_
.
data
();
225
}
226
227
template
<
std
::
size_t
N
>
228
bool
SmallString
<
N
>::
empty
()
const
noexcept
{
229
return
data_
.
empty
();
230
}
231
232
template
<
std
::
size_t
N
>
233
char
&
SmallString
<
N
>::
front
() {
234
return
data_
.
front
();
235
}
236
237
template
<
std
::
size_t
N
>
238
const
char
&
SmallString
<
N
>::
front
()
const
{
239
return
data_
.
front
();
240
}
241
242
template
<
std
::
size_t
N
>
243
char
&
SmallString
<
N
>::
back
() {
244
return
data_
.
back
();
245
}
246
247
template
<
std
::
size_t
N
>
248
const
char
&
SmallString
<
N
>::
back
()
const
{
249
return
data_
.
back
();
250
}
251
252
template
<
std
::
size_t
N
>
253
void
SmallString
<
N
>::
push_back
(
char
c
) {
254
data_
.
push_back
(
c
);
255
}
256
257
template
<
std
::
size_t
N
>
258
void
SmallString
<
N
>::
append
(
std
::
string_view
str
) {
259
std
::
size_t
old_size
=
data_
.
size
();
260
data_
.
insert
(
data_
.
begin
() +
old_size
,
str
.
begin
(),
str
.
end
());
261
}
262
263
template
<
std
::
size_t
N
>
264
void
SmallString
<
N
>::
pop_back
() {
265
data_
.
pop_back
();
266
}
267
268
template
<
std
::
size_t
N
>
269
void
SmallString
<
N
>::
resize
(
std
::
size_t
n
,
char
c
) {
270
data_
.
resize
(
n
,
c
);
271
}
272
273
template
<
std
::
size_t
N
>
274
template
<
class
Operation
>
275
void
SmallString
<
N
>::
resize_and_overwrite
(
std
::
size_t
size
,
Operation
op
) {
276
data_
.
resize
(
size
,
boost
::
container
::
default_init
);
277
data_
.
resize
(
std
::
move
(
op
)(
data_
.
data
(),
size
),
boost
::
container
::
default_init
);
278
UASSERT
(
data_
.
size
() <=
size
);
279
}
280
281
template
<
std
::
size_t
N
>
282
void
SmallString
<
N
>::
shrink_to_fit
() {
283
data_
.
shrink_to_fit
();
284
}
285
286
template
<
std
::
size_t
N
>
287
std
::
size_t
SmallString
<
N
>::
capacity
()
const
noexcept
{
288
return
data_
.
capacity
();
289
}
290
291
template
<
std
::
size_t
N
>
292
void
SmallString
<
N
>::
reserve
(
std
::
size_t
n
) {
293
return
data_
.
reserve
(
n
);
294
}
295
296
template
<
std
::
size_t
N
>
297
void
SmallString
<
N
>::
clear
()
noexcept
{
298
data_
.
clear
();
299
}
300
301
}
// namespace utils
302
303
USERVER_NAMESPACE_END
304
305
template
<std::size_t N>
306
struct
std::hash<USERVER_NAMESPACE::
utils
::
SmallString
<N>> {
307
std::size_t operator()(
const
USERVER_NAMESPACE::
utils
::
SmallString
<N>& s)
const
noexcept
{
308
return
std::hash<std::string_view>{}(std::string_view{s});
309
}
310
};
userver
utils
small_string.hpp
Generated on Wed Dec 4 2024 18:51:16 for userver by
Doxygen
1.10.0