Embedded Template Library 1.0
Loading...
Searching...
No Matches
string.h
Go to the documentation of this file.
1
2
3/******************************************************************************
4The MIT License(MIT)
5
6Embedded Template Library.
7https://github.com/ETLCPP/etl
8https://www.etlcpp.com
9
10Copyright(c) 2016 John Wellbelove
11
12Permission is hereby granted, free of charge, to any person obtaining a copy
13of this software and associated documentation files(the "Software"), to deal
14in the Software without restriction, including without limitation the rights
15to use, copy, modify, merge, publish, distribute, sublicense, and / or sell
16copies of the Software, and to permit persons to whom the Software is
17furnished to do so, subject to the following conditions :
18
19The above copyright notice and this permission notice shall be included in all
20copies or substantial portions of the Software.
21
22THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
23IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
24FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.IN NO EVENT SHALL THE
25AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
26LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
27OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
28SOFTWARE.
29******************************************************************************/
30
31#ifndef ETL_STRING_INCLUDED
32#define ETL_STRING_INCLUDED
33
34#include "platform.h"
35#include "basic_string.h"
36#include "string_view.h"
37#include "hash.h"
38#include "initializer_list.h"
39
40#include <ctype.h>
41
42#include "private/minmax_push.h"
43
44namespace etl
45{
46#if ETL_USING_CPP11
47 inline namespace literals
48 {
49 inline namespace string_literals
50 {
51 inline constexpr etl::string_view operator ""_sv(const char* str, size_t length) ETL_NOEXCEPT
52 {
53 return etl::string_view{ str, length };
54 }
55 }
56 }
57#endif
58
59 typedef etl::ibasic_string<char> istring;
60
61 //***************************************************************************
65 //***************************************************************************
66 template <size_t MAX_SIZE_>
67 class string : public istring
68 {
69 public:
70
71 typedef istring base_type;
72 typedef istring interface_type;
73
74 typedef istring::value_type value_type;
75 typedef istring::size_type size_type;
76
77 static ETL_CONSTANT size_t MAX_SIZE = MAX_SIZE_;
78
79 //*************************************************************************
81 //*************************************************************************
83 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
84 {
85 this->initialise();
86 }
87
88 //*************************************************************************
91 //*************************************************************************
93 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
94 {
95 this->initialise();
96 this->assign(other);
97 }
98
99 //*************************************************************************
102 //*************************************************************************
103 string(const etl::istring& other)
104 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
105 {
106 this->initialise();
107 this->assign(other);
108 }
109
110 //*************************************************************************
115 //*************************************************************************
116 string(const etl::istring& other, size_t position, size_t length = npos)
117 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
118 {
119 ETL_ASSERT(position < other.size(), ETL_ERROR(string_out_of_bounds));
120
121 this->initialise();
122 this->assign(other, position, length);
123 }
124
125 //*************************************************************************
128 //*************************************************************************
129 ETL_EXPLICIT_STRING_FROM_CHAR string(const value_type* text)
130 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
131 {
132 this->initialise();
133 this->assign(text);
134 }
135
136 //*************************************************************************
140 //*************************************************************************
141 string(const value_type* text, size_t count)
142 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
143 {
144 this->initialise();
145 this->assign(text, text + count);
146 }
147
148 //*************************************************************************
152 //*************************************************************************
153 string(size_type count, value_type c)
154 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
155 {
156 this->initialise();
157 this->resize(count, c);
158 }
159
160 //*************************************************************************
165 //*************************************************************************
166 template <typename TIterator>
167 string(TIterator first, TIterator last, typename etl::enable_if<!etl::is_integral<TIterator>::value, int>::type = 0)
168 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
169 {
170 this->initialise();
171 this->assign(first, last);
172 }
173
174#if ETL_HAS_INITIALIZER_LIST
175 //*************************************************************************
177 //*************************************************************************
178 string(std::initializer_list<value_type> init)
179 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
180 {
181 this->initialise();
182 this->assign(init.begin(), init.end());
183 }
184#endif
185
186 //*************************************************************************
189 //*************************************************************************
190 explicit string(const etl::string_view& view)
191 : istring(reinterpret_cast<value_type*>(&buffer), MAX_SIZE)
192 {
193 this->initialise();
194 this->assign(view.begin(), view.end());
195 }
196
197 //*************************************************************************
201 //*************************************************************************
202 etl::string<MAX_SIZE_> substr(size_type position = 0, size_type length_ = npos) const
203 {
204 etl::string<MAX_SIZE_> new_string;
205
206 if (position != this->size())
207 {
208 ETL_ASSERT(position < this->size(), ETL_ERROR(string_out_of_bounds));
209
210 length_ = etl::min(length_, this->size() - position);
211
212 new_string.assign(buffer + position, buffer + position + length_);
213 }
214
215 return new_string;
216 }
217
218 //*************************************************************************
220 //*************************************************************************
221 string& operator = (const string& rhs)
222 {
223 if (&rhs != this)
224 {
225 this->assign(rhs);
226 }
227
228 return *this;
229 }
230
231
232 //*************************************************************************
234 //*************************************************************************
235 string& operator = (const istring& rhs)
236 {
237 if (&rhs != this)
238 {
239 this->assign(rhs);
240 }
241
242 return *this;
243 }
244
245 //*************************************************************************
247 //*************************************************************************
248 string& operator = (const value_type* text)
249 {
250 this->assign(text);
251
252 return *this;
253 }
254
255 //*************************************************************************
257 //*************************************************************************
258 string& operator = (const etl::string_view& view)
259 {
260 this->assign(view);
261
262 return *this;
263 }
264
265 //*************************************************************************
267 //*************************************************************************
268#if ETL_HAS_ISTRING_REPAIR
269 virtual void repair() ETL_OVERRIDE
270#else
271 void repair()
272#endif
273 {
275 }
276
277 private:
278
279 value_type buffer[MAX_SIZE + 1];
280 };
281
282 template <size_t MAX_SIZE_>
283 ETL_CONSTANT typename string<MAX_SIZE_>::size_type string<MAX_SIZE_>::MAX_SIZE;
284
285 //***************************************************************************
288 //***************************************************************************
289 class string_ext : public istring
290 {
291 public:
292
293 typedef istring base_type;
294 typedef istring interface_type;
295
296 typedef istring::value_type value_type;
297 typedef istring::size_type size_type;
298
299 //*************************************************************************
301 //*************************************************************************
302 string_ext(value_type* buffer, size_type buffer_size)
303 : istring(buffer, buffer_size - 1U)
304 {
305 this->initialise();
306 }
307
308 //*************************************************************************
311 //*************************************************************************
312 string_ext(const etl::string_ext& other, value_type* buffer, size_type buffer_size)
313 : istring(buffer, buffer_size - 1U)
314 {
315 if (this->is_within_buffer(other.data()))
316 {
317 this->current_size = other.size();
318 }
319 else
320 {
321 this->initialise();
322 this->assign(other);
323 }
324 }
325
326 //*************************************************************************
329 //*************************************************************************
330 string_ext(const etl::istring& other, value_type* buffer, size_type buffer_size)
331 : istring(buffer, buffer_size - 1U)
332 {
333 if (this->is_within_buffer(other.data()))
334 {
335 this->current_size = other.size();
336 }
337 else
338 {
339 this->initialise();
340 this->assign(other);
341 }
342 }
343
344 //*************************************************************************
349 //*************************************************************************
350 string_ext(const etl::istring& other, value_type* buffer, size_type buffer_size, size_type position, size_type length = npos)
351 : istring(buffer, buffer_size - 1U)
352 {
353 ETL_ASSERT(position < other.size(), ETL_ERROR(string_out_of_bounds));
354
355 if (this->is_within_buffer(other.data()))
356 {
357 this->current_size = other.size();
358 }
359 else
360 {
361 this->initialise();
362 this->assign(other, position, length);
363 }
364 }
365
366 //*************************************************************************
369 //*************************************************************************
370 template <typename TPointer>
371 string_ext(TPointer text, value_type* buffer, size_type buffer_size,
373 : istring(buffer, buffer_size - 1U)
374 {
375 if (this->is_within_buffer(text))
376 {
377 this->current_size = etl::strlen(buffer);
378 }
379 else
380 {
381 this->initialise();
382 this->assign(text, text + etl::strlen(text));
383 }
384 }
385
386 //*************************************************************************
389 //*************************************************************************
390 template <size_t Size>
391 string_ext(const value_type (&literal)[Size], value_type* buffer, size_type buffer_size)
392 : istring(buffer, buffer_size - 1U)
393 {
394 if (this->is_within_buffer(literal))
395 {
396 this->current_size = etl::strlen(literal);
397 }
398 else
399 {
400 this->initialise();
401 this->assign(literal);
402 }
403 }
404
405 //*************************************************************************
409 //*************************************************************************
410 string_ext(const value_type* text, size_type count, value_type* buffer, size_type buffer_size)
411 : istring(buffer, buffer_size - 1U)
412 {
413 if (this->is_within_buffer(text))
414 {
415 this->current_size = count;
416 }
417 else
418 {
419 this->initialise();
420 this->assign(text, text + count);
421 }
422 }
423
424 //*************************************************************************
428 //*************************************************************************
429 string_ext(size_type count, value_type c, value_type* buffer, size_type buffer_size)
430 : istring(buffer, buffer_size - 1U)
431 {
432 this->initialise();
433 this->resize(count, c);
434 }
435
436 //*************************************************************************
439 //*************************************************************************
440 explicit string_ext(const etl::string_view& view, value_type* buffer, size_type buffer_size)
441 : istring(buffer, buffer_size - 1U)
442 {
443 if (this->is_within_buffer(view.data()))
444 {
445 this->current_size = view.size();
446 }
447 else
448 {
449 this->initialise();
450 this->assign(view.begin(), view.end());
451 }
452 }
453
454 //*************************************************************************
459 //*************************************************************************
460 template <typename TIterator>
461 string_ext(TIterator first, TIterator last, value_type* buffer, size_type buffer_size, typename etl::enable_if<!etl::is_integral<TIterator>::value, int>::type = 0)
462 : istring(buffer, buffer_size - 1U)
463 {
464 if (this->is_within_buffer(etl::addressof(*first)))
465 {
466 this->current_size = etl::distance(first, last);
467 }
468 else
469 {
470 this->initialise();
471 this->assign(first, last);
472 }
473 }
474
475#if ETL_HAS_INITIALIZER_LIST
476 //*************************************************************************
478 //*************************************************************************
479 string_ext(std::initializer_list<value_type> init, value_type* buffer, size_type buffer_size)
480 : istring(buffer, buffer_size - 1U)
481 {
482 this->initialise();
483 this->assign(init.begin(), init.end());
484 }
485#endif
486
487 //*************************************************************************
489 //*************************************************************************
491 {
492 if (&rhs != this)
493 {
494 this->assign(rhs);
495 }
496
497 return *this;
498 }
499
500 //*************************************************************************
502 //*************************************************************************
503 string_ext& operator = (const istring& rhs)
504 {
505 if (&rhs != this)
506 {
507 this->assign(rhs);
508 }
509
510 return *this;
511 }
512
513 //*************************************************************************
515 //*************************************************************************
516 string_ext& operator = (const value_type* text)
517 {
518 this->assign(text);
519
520 return *this;
521 }
522
523 //*************************************************************************
525 //*************************************************************************
526 string_ext& operator = (const etl::string_view& view)
527 {
528 this->assign(view);
529
530 return *this;
531 }
532
533 //*************************************************************************
535 //*************************************************************************
536#if ETL_HAS_ISTRING_REPAIR
537 virtual void repair() ETL_OVERRIDE
538#else
539 void repair()
540#endif
541 {
542 }
543
544 private:
545
546 //*************************************************************************
548 //*************************************************************************
549 string_ext(const string_ext& other) ETL_DELETE;
550 };
551
552 //*************************************************************************
554 //*************************************************************************
555#if ETL_USING_8BIT_TYPES
556 template <>
557 struct hash<etl::istring>
558 {
559 size_t operator()(const etl::istring& text) const
560 {
561 return etl::private_hash::generic_hash<size_t>(reinterpret_cast<const uint8_t*>(text.data()),
562 reinterpret_cast<const uint8_t*>(text.data() + text.size()));
563 }
564 };
565
566 template <size_t SIZE>
567 struct hash<etl::string<SIZE> >
568 {
569 size_t operator()(const etl::string<SIZE>& text) const
570 {
571 return etl::private_hash::generic_hash<size_t>(reinterpret_cast<const uint8_t*>(text.data()),
572 reinterpret_cast<const uint8_t*>(text.data() + text.size()));
573 }
574 };
575
576 template <>
577 struct hash<etl::string_ext>
578 {
579 size_t operator()(const etl::string_ext& text) const
580 {
581 return etl::private_hash::generic_hash<size_t>(reinterpret_cast<const uint8_t*>(text.data()),
582 reinterpret_cast<const uint8_t*>(text.data() + text.size()));
583 }
584 };
585#endif
586
587 //***************************************************************************
589 //***************************************************************************
590 template<size_t Array_Size>
591 etl::string<Array_Size - 1U> make_string(const char(&text)[Array_Size])
592 {
593 return etl::string<Array_Size - 1U>(text, etl::strlen(text, Array_Size - 1));
594 }
595
596 //***************************************************************************
598 //***************************************************************************
599 template<size_t MAX_SIZE, size_t SIZE>
601 {
602 return etl::string<MAX_SIZE>(text, etl::strlen(text, SIZE));
603 }
604}
605
606#include "private/minmax_pop.h"
607
608#endif
ETL_CONSTEXPR const_pointer data() const ETL_NOEXCEPT
Returns a const pointer to the first element of the internal storage.
Definition string_view.h:196
ETL_CONSTEXPR const_iterator end() const ETL_NOEXCEPT
Returns a const iterator to the end of the array.
Definition string_view.h:220
ETL_CONSTEXPR const_iterator begin() const ETL_NOEXCEPT
Returns a const iterator to the beginning of the array.
Definition string_view.h:204
bool is_within_buffer(const_pointer ptr) const
Definition basic_string.h:2718
void resize(size_type new_size)
Definition basic_string.h:481
void assign(const etl::ibasic_string< char > &other)
Definition basic_string.h:683
pointer data()
Definition basic_string.h:646
void initialise()
Definition basic_string.h:2491
void repair_buffer(char *p_buffer_)
Definition basic_string.h:2503
size_type length() const
Definition basic_string.h:202
size_type current_size
The current number of elements in the string.
Definition basic_string.h:336
size_type size() const
Definition basic_string.h:193
Definition string.h:290
string_ext(const etl::istring &other, value_type *buffer, size_type buffer_size, size_type position, size_type length=npos)
Definition string.h:350
string_ext(value_type *buffer, size_type buffer_size)
Constructor.
Definition string.h:302
string_ext(const etl::string_ext &other, value_type *buffer, size_type buffer_size)
Definition string.h:312
string_ext(const etl::string_view &view, value_type *buffer, size_type buffer_size)
Definition string.h:440
string_ext(size_type count, value_type c, value_type *buffer, size_type buffer_size)
Definition string.h:429
string_ext(const etl::istring &other, value_type *buffer, size_type buffer_size)
Definition string.h:330
string_ext(const value_type(&literal)[Size], value_type *buffer, size_type buffer_size)
Definition string.h:391
string_ext(TPointer text, value_type *buffer, size_type buffer_size, typename etl::enable_if< etl::is_same< const value_type *, TPointer >::value, int >::type *=ETL_NULLPTR)
Definition string.h:371
void repair()
Fix the internal pointers after a low level memory copy.
Definition string.h:539
string_ext(const value_type *text, size_type count, value_type *buffer, size_type buffer_size)
Definition string.h:410
string_ext(TIterator first, TIterator last, value_type *buffer, size_type buffer_size, typename etl::enable_if<!etl::is_integral< TIterator >::value, int >::type=0)
Definition string.h:461
string_ext & operator=(const string_ext &rhs)
Assignment operator.
Definition string.h:490
Definition basic_string.h:115
Definition string.h:68
etl::string< MAX_SIZE_ > substr(size_type position=0, size_type length_=npos) const
Definition string.h:202
void repair()
Fix the internal pointers after a low level memory copy.
Definition string.h:271
string()
Constructor.
Definition string.h:82
string(TIterator first, TIterator last, typename etl::enable_if<!etl::is_integral< TIterator >::value, int >::type=0)
Definition string.h:167
string(const etl::string_view &view)
Definition string.h:190
string(const etl::string< MAX_SIZE_ > &other)
Definition string.h:92
string(const etl::istring &other)
Definition string.h:103
string & operator=(const string &rhs)
Assignment operator.
Definition string.h:221
string(const etl::istring &other, size_t position, size_t length=npos)
Definition string.h:116
string(const value_type *text, size_t count)
Definition string.h:141
ETL_EXPLICIT_STRING_FROM_CHAR string(const value_type *text)
Definition string.h:129
string(size_type count, value_type c)
Definition string.h:153
#define ETL_ASSERT(b, e)
Definition error_handler.h:356
ETL_CONSTEXPR17 etl::enable_if<!etl::is_same< T, etl::nullptr_t >::value, T >::type * addressof(T &t)
Definition addressof.h:52
enable_if
Definition type_traits_generator.h:1254
is_same
Definition type_traits_generator.h:1104
bitset_ext
Definition absolute.h:39
etl::string< Array_Size - 1U > make_string(const char(&text)[Array_Size])
Hash function.
Definition string.h:591
etl::string< MAX_SIZE > make_string_with_capacity(const char(&text)[SIZE])
Make string with max capacity from string literal or array.
Definition string.h:600
ETL_CONSTEXPR14 size_t strlen(const T *t) ETL_NOEXCEPT
Alternative strlen for all character types.
Definition char_traits.h:287