Embedded Template Library 1.0
Loading...
Searching...
No Matches
span.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) 2020 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_SPAN_INCLUDED
32#define ETL_SPAN_INCLUDED
33
34#include "platform.h"
35
36#include "error_handler.h"
37#include "exception.h"
38#include "alignment.h"
39#include "iterator.h"
40#include "algorithm.h"
41#include "circular_iterator.h"
42#include "nullptr.h"
43#include "hash.h"
44#include "type_traits.h"
45#include "integral_limits.h"
46#include "memory.h"
47#include "array.h"
48#include "byte.h"
49#include "static_assert.h"
50
52
55
56namespace etl
57{
58 template <typename T> struct is_std_array : etl::false_type {};
59#if ETL_USING_STL && ETL_USING_CPP11
60 template <typename T, size_t N> struct is_std_array<std::array<T, N>> : etl::true_type {};
61#endif
62 template <typename T> struct is_std_array<const T> : is_std_array<T> {};
63 template <typename T> struct is_std_array<volatile T> : is_std_array<T> {};
64 template <typename T> struct is_std_array<const volatile T> : is_std_array<T> {};
65
66 template <typename T> struct is_etl_array : etl::false_type {};
67 template <typename T, size_t N> struct is_etl_array<etl::array<T, N> > : etl::true_type {};
68 template <typename T> struct is_etl_array<const T> : is_etl_array<T> {};
69 template <typename T> struct is_etl_array<volatile T> : is_etl_array<T> {};
70 template <typename T> struct is_etl_array<const volatile T> : is_etl_array<T> {};
71
72 //***************************************************************************
73 // Tag to indicate a class is a span.
74 //***************************************************************************
75 class span_tag {};
76
77 //***************************************************************************
80 //***************************************************************************
81 class span_exception : public exception
82 {
83 public:
84
85 span_exception(string_type reason_, string_type file_name_, numeric_type line_number_)
86 : exception(reason_, file_name_, line_number_)
87 {
88 }
89 };
90
91 //***************************************************************************
94 //***************************************************************************
95 class span_alignment_exception : public span_exception
96 {
97 public:
98
99 span_alignment_exception(string_type file_name_, numeric_type line_number_)
100 : span_exception(ETL_ERROR_TEXT("span:alignment", ETL_SPAN_FILE_ID"A"), file_name_, line_number_)
101 {
102 }
103 };
104
105 //***************************************************************************
108 //***************************************************************************
109 class span_size_mismatch : public span_exception
110 {
111 public:
112
113 span_size_mismatch(string_type file_name_, numeric_type line_number_)
114 : span_exception(ETL_ERROR_TEXT("span:size", ETL_SPAN_FILE_ID"B"), file_name_, line_number_)
115 {
116 }
117 };
118
119 //***************************************************************************
122 //***************************************************************************
123 class span_out_of_range : public span_exception
124 {
125 public:
126
127 span_out_of_range(string_type file_name_, numeric_type line_number_)
128 : span_exception(ETL_ERROR_TEXT("span:range", ETL_SPAN_FILE_ID"C"), file_name_, line_number_)
129 {
130 }
131 };
132
133 //***************************************************************************
135 //***************************************************************************
136 template <typename T, size_t Extent = etl::dynamic_extent>
137 class span : public span_tag
138 {
139 public:
140
141 typedef T element_type;
142 typedef typename etl::remove_cv<T>::type value_type;
143 typedef size_t size_type;
144 typedef T& reference;
145 typedef const T& const_reference;
146 typedef T* pointer;
147 typedef const T* const_pointer;
148
149 typedef T* iterator;
150 typedef const T* const_iterator;
151 typedef ETL_OR_STD::reverse_iterator<iterator> reverse_iterator;
152 typedef ETL_OR_STD::reverse_iterator<const_iterator> const_reverse_iterator;
153
154 typedef etl::circular_iterator<pointer> circular_iterator;
155 typedef etl::circular_iterator<ETL_OR_STD::reverse_iterator<pointer> > reverse_circular_iterator;
156
157 static ETL_CONSTANT size_t extent = Extent;
158
159 //*************************************************************************
161 //*************************************************************************
162 template <typename TIterator, typename TSize>
163 ETL_CONSTEXPR explicit span(const TIterator begin_, const TSize /*size_*/) ETL_NOEXCEPT
164 : pbegin(etl::to_address(begin_))
165 {
166 }
167
168 //*************************************************************************
170 //*************************************************************************
171 template <typename TIterator>
172 ETL_CONSTEXPR explicit span(const TIterator begin_, const TIterator /*end_*/) ETL_NOEXCEPT
173 : pbegin(etl::to_address(begin_))
174 {
175 }
176
177 //*************************************************************************
179 //*************************************************************************
180#if ETL_USING_CPP11
181 template<size_t Array_Size, typename = typename etl::enable_if<(Array_Size == Extent), void>::type>
182 ETL_CONSTEXPR span(element_type(&begin_)[Array_Size]) ETL_NOEXCEPT
183 : pbegin(begin_)
184 {
185 }
186#else
187 //*************************************************************************
189 //*************************************************************************
190 template<size_t Array_Size>
191 ETL_CONSTEXPR span(element_type(&begin_)[Array_Size], typename etl::enable_if<(Array_Size == Extent), void>::type* = 0) ETL_NOEXCEPT
192 : pbegin(begin_)
193 {
194 }
195#endif
196
197#if ETL_USING_CPP11
198 //*************************************************************************
201 //*************************************************************************
202 template <typename TContainer, typename = typename etl::enable_if<!etl::is_base_of<span_tag, etl::remove_reference_t<TContainer>>::value &&
203 !etl::is_std_array<etl::remove_reference_t<TContainer>>::value &&
204 !etl::is_etl_array<etl::remove_reference_t<TContainer>>::value &&
205 !etl::is_pointer<etl::remove_reference_t<TContainer>>::value &&
206 !etl::is_array<etl::remove_reference_t<TContainer>>::value &&
207 etl::is_same<etl::remove_cv_t<T>, etl::remove_cv_t<typename etl::remove_reference_t<TContainer>::value_type>>::value, void>::type>
208 ETL_CONSTEXPR span(TContainer&& a) ETL_NOEXCEPT
209 : pbegin(a.data())
210 {
211 }
212#else
213 //*************************************************************************
216 //*************************************************************************
217 template <typename TContainer>
218 span(TContainer& a, typename etl::enable_if<!etl::is_base_of<span_tag, typename etl::remove_reference<TContainer>::type>::value &&
219 !etl::is_std_array<typename etl::remove_reference<TContainer>::type>::value &&
220 !etl::is_etl_array<typename etl::remove_reference<TContainer>::type>::value &&
221 !etl::is_pointer<typename etl::remove_reference<TContainer>::type>::value &&
223 etl::is_same<typename etl::remove_cv<T>::type, typename etl::remove_cv<typename etl::remove_reference<TContainer>::type::value_type>::type>::value, void>::type* = 0) ETL_NOEXCEPT
224 : pbegin(a.data())
225 {
226 }
227
228 //*************************************************************************
231 //*************************************************************************
232 template <typename TContainer>
233 span(const TContainer& a, typename etl::enable_if<!etl::is_base_of<span_tag, typename etl::remove_reference<TContainer>::type>::value &&
234 !etl::is_std_array<typename etl::remove_reference<TContainer>::type>::value &&
235 !etl::is_etl_array<typename etl::remove_reference<TContainer>::type>::value &&
236 !etl::is_pointer<typename etl::remove_reference<TContainer>::type>::value &&
238 etl::is_same<typename etl::remove_cv<T>::type, typename etl::remove_cv<typename etl::remove_reference<TContainer>::type::value_type>::type>::value, void>::type* = 0) ETL_NOEXCEPT
239 : pbegin(a.data())
240 {
241 }
242#endif
243
244 //*************************************************************************
246 //*************************************************************************
247 ETL_CONSTEXPR span(const span& other) ETL_NOEXCEPT
248 : pbegin(other.pbegin)
249 {
250 }
251
252 //*************************************************************************
255 //*************************************************************************
256 template <typename U, size_t Size>
257 ETL_CONSTEXPR span(const etl::span<U, Size>& other, typename etl::enable_if<Size == Extent, void>::type* = 0) ETL_NOEXCEPT
258 : pbegin(other.data())
259 {
260 }
261
262 //*************************************************************************
265 //*************************************************************************
266 template <typename U, size_t Size>
268 : pbegin(other.data())
269 {
270 ETL_ASSERT(other.size() == Extent, ETL_ERROR(span_size_mismatch));
271 }
272
273#if ETL_USING_STL && ETL_USING_CPP11
274 //*************************************************************************
276 //*************************************************************************
277 template <typename U, size_t Size>
278 ETL_CONSTEXPR span(std::array<U, Size>& other, typename etl::enable_if<Size == Extent, void>::type* = 0) ETL_NOEXCEPT
279 : pbegin(other.data())
280 {
281 }
282
283 //*************************************************************************
285 //*************************************************************************
286 template <typename U, size_t Size>
287 ETL_CONSTEXPR span(const std::array<U, Size>& other, typename etl::enable_if<Size == Extent && etl::is_const<T>::value, void>::type* = 0) ETL_NOEXCEPT
288 : pbegin(other.data())
289 {
290 }
291#endif
292
293 //*************************************************************************
295 //*************************************************************************
296 template <typename U, size_t Size>
297 ETL_CONSTEXPR span(etl::array<U, Size>& other, typename etl::enable_if<Size == Extent, void>::type* = 0) ETL_NOEXCEPT
298 : pbegin(other.data())
299 {
300 }
301
302 //*************************************************************************
304 //*************************************************************************
305 template <typename U, size_t Size>
306 ETL_CONSTEXPR span(const etl::array<U, Size>& other, typename etl::enable_if<Size == Extent && etl::is_const<T>::value, void>::type* = 0) ETL_NOEXCEPT
307 : pbegin(other.data())
308 {
309 }
310
311 //*************************************************************************
313 //*************************************************************************
314 ETL_NODISCARD ETL_CONSTEXPR reference front() const ETL_NOEXCEPT
315 {
316 ETL_STATIC_ASSERT(Extent > 0, "Span is empty");
317
318 return *pbegin;
319 }
320
321 //*************************************************************************
323 //*************************************************************************
324 ETL_NODISCARD ETL_CONSTEXPR reference back() const ETL_NOEXCEPT
325 {
326 ETL_STATIC_ASSERT(Extent > 0, "Span is empty");
327
328 return *((pbegin + Extent) - 1);
329 }
330
331 //*************************************************************************
333 //*************************************************************************
334 ETL_NODISCARD ETL_CONSTEXPR pointer data() const ETL_NOEXCEPT
335 {
336 return pbegin;
337 }
338
339 //*************************************************************************
341 //*************************************************************************
342 ETL_NODISCARD ETL_CONSTEXPR const_iterator cbegin() const ETL_NOEXCEPT
343 {
344 return pbegin;
345 }
346
347 //*************************************************************************
349 //*************************************************************************
350 ETL_NODISCARD ETL_CONSTEXPR iterator begin() const ETL_NOEXCEPT
351 {
352 return pbegin;
353 }
354
355 //*************************************************************************
357 //*************************************************************************
358 ETL_NODISCARD ETL_CONSTEXPR circular_iterator begin_circular() const ETL_NOEXCEPT
359 {
360 return circular_iterator(begin(), end());
361 }
362
363 //*************************************************************************
365 //*************************************************************************
366 ETL_NODISCARD ETL_CONSTEXPR const_iterator cend() const ETL_NOEXCEPT
367 {
368 return (pbegin + Extent);
369 }
370
371 //*************************************************************************
373 //*************************************************************************
374 ETL_NODISCARD ETL_CONSTEXPR iterator end() const ETL_NOEXCEPT
375 {
376 return (pbegin + Extent);
377 }
378
379 //*************************************************************************
380 // Returns a const reverse iterator to the reverse beginning of the span.
381 //*************************************************************************
382 ETL_NODISCARD ETL_CONSTEXPR const_reverse_iterator crbegin() const ETL_NOEXCEPT
383 {
384 return const_reverse_iterator((pbegin + Extent));
385 }
386
387 //*************************************************************************
388 // Returns an reverse iterator to the reverse beginning of the span.
389 //*************************************************************************
390 ETL_NODISCARD ETL_CONSTEXPR reverse_iterator rbegin() const ETL_NOEXCEPT
391 {
392 return reverse_iterator((pbegin + Extent));
393 }
394
395 //*************************************************************************
397 //*************************************************************************
398 ETL_NODISCARD ETL_CONSTEXPR reverse_circular_iterator rbegin_circular() const ETL_NOEXCEPT
399 {
400 return reverse_circular_iterator(rbegin(), rend());
401 }
402
403 //*************************************************************************
405 //*************************************************************************
406 ETL_NODISCARD ETL_CONSTEXPR const_reverse_iterator crend() const ETL_NOEXCEPT
407 {
408 return const_reverse_iterator(pbegin);
409 }
410
411 //*************************************************************************
413 //*************************************************************************
414 ETL_NODISCARD ETL_CONSTEXPR reverse_iterator rend() const ETL_NOEXCEPT
415 {
416 return reverse_iterator(pbegin);
417 }
418
419 //*************************************************************************
421 //*************************************************************************
422 ETL_NODISCARD ETL_CONSTEXPR bool empty() const ETL_NOEXCEPT
423 {
424 return Extent == 0;
425 }
426
427 //*************************************************************************
429 //*************************************************************************
430 ETL_NODISCARD ETL_CONSTEXPR size_t size() const ETL_NOEXCEPT
431 {
432 return Extent;
433 }
434
435 //*************************************************************************
437 //*************************************************************************
438 ETL_NODISCARD ETL_CONSTEXPR size_t size_bytes() const ETL_NOEXCEPT
439 {
440 return sizeof(element_type) * Extent;
441 }
442
443 //*************************************************************************
445 //*************************************************************************
446 ETL_NODISCARD ETL_CONSTEXPR size_t max_size() const ETL_NOEXCEPT
447 {
448 return size();
449 }
450
451 //*************************************************************************
453 //*************************************************************************
454 ETL_CONSTEXPR14 span& operator =(const span& other) ETL_NOEXCEPT
455 {
456 pbegin = other.pbegin;
457 return *this;
458 }
459
460 //*************************************************************************
462 //*************************************************************************
463 ETL_NODISCARD ETL_CONSTEXPR14 reference at(size_t i)
464 {
465 ETL_ASSERT(i < size(), ETL_ERROR(span_out_of_range));
466
467 return pbegin[i];
468 }
469
470 //*************************************************************************
472 //*************************************************************************
473 ETL_NODISCARD ETL_CONSTEXPR14 const_reference at(size_t i) const
474 {
475 ETL_ASSERT(i < size(), ETL_ERROR(span_out_of_range));
476
477 return pbegin[i];
478 }
479
480 //*************************************************************************
482 //*************************************************************************
483 ETL_CONSTEXPR reference operator[](const size_t i) const
484 {
485#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_INDEX_OPERATOR
486 return i < size() ? pbegin[i] : throw(ETL_ERROR(span_out_of_range));
487#else
488 ETL_ASSERT_CHECK_INDEX_OPERATOR(i < size(), ETL_ERROR(span_out_of_range));
489
490 return pbegin[i];
491#endif
492 }
493
494 //*************************************************************************
496 //*************************************************************************
497 template <size_t COUNT>
498 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, COUNT> first() const ETL_NOEXCEPT
499 {
500 // If Extent is static, check that original span contains at least COUNT elements
501 ETL_STATIC_ASSERT(COUNT <= Extent, "Original span does not contain COUNT elements");
502
503 return etl::span<element_type, COUNT>(pbegin, pbegin + COUNT);
504 }
505
506 //*************************************************************************
508 //*************************************************************************
509 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, etl::dynamic_extent> first(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
510 {
511#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
512 return count <= size() ? etl::span<element_type, etl::dynamic_extent>(pbegin, pbegin + count) : throw(ETL_ERROR(span_out_of_range));
513#else
514 ETL_ASSERT_CHECK_EXTRA(count <= size(), ETL_ERROR(span_out_of_range));
515
516 return etl::span<element_type, etl::dynamic_extent>(pbegin, pbegin + count);
517#endif
518 }
519
520 //*************************************************************************
522 //*************************************************************************
523 template <size_t COUNT>
524 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, COUNT> last() const ETL_NOEXCEPT
525 {
526 // If Extent is static, check that original span contains at least COUNT elements
527 ETL_STATIC_ASSERT(COUNT <= Extent, "Original span does not contain COUNT elements");
528
529 return etl::span<element_type, COUNT>(pbegin + Extent - COUNT, (pbegin + Extent));
530 }
531
532 //*************************************************************************
534 //*************************************************************************
535 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, etl::dynamic_extent> last(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
536 {
537#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
538 return count <= size() ?
539 etl::span<element_type, etl::dynamic_extent>((pbegin + Extent) - count, (pbegin + Extent)) :
540 throw(ETL_ERROR(span_out_of_range));
541#else
542 ETL_ASSERT_CHECK_EXTRA(count <= size(), ETL_ERROR(span_out_of_range));
543
544 return etl::span<element_type, etl::dynamic_extent>((pbegin + Extent) - count, (pbegin + Extent));
545#endif
546 }
547
548#if ETL_USING_CPP11
549 //*************************************************************************
551 //*************************************************************************
552 template <size_t OFFSET, size_t COUNT = etl::dynamic_extent>
553 ETL_NODISCARD ETL_CONSTEXPR
554 etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : Extent - OFFSET> subspan() const ETL_NOEXCEPT
555 {
556 // If Extent is static, check that OFFSET is within the original span
557 ETL_STATIC_ASSERT(OFFSET <= Extent, "OFFSET is not within the original span");
558
559 // If count is also static, check that OFFSET + COUNT is within the original span
560 ETL_STATIC_ASSERT((COUNT != etl::dynamic_extent) ? COUNT <= (Extent - OFFSET) : true, "OFFSET + COUNT is not within the original span");
561
562 return (COUNT == etl::dynamic_extent) ? etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : Extent - OFFSET>(pbegin + OFFSET, (pbegin + Extent))
563 : etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : Extent - OFFSET>(pbegin + OFFSET, pbegin + OFFSET + COUNT);
564 }
565#else
566 //*************************************************************************
568 //*************************************************************************
569 template <size_t OFFSET, size_t COUNT>
570 etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : Extent - OFFSET> subspan() const
571 {
572 // If Extent is static, check that OFFSET is within the original span
573 ETL_STATIC_ASSERT(OFFSET <= Extent, "OFFSET is not within the original span");
574
575 // If count is also static, check that OFFSET + COUNT is within the original span
576 ETL_STATIC_ASSERT((COUNT != etl::dynamic_extent) ? COUNT <= (Extent - OFFSET) : true, "OFFSET + COUNT is not within the original span");
577
578 if (COUNT == etl::dynamic_extent)
579 {
580 return etl::span<element_type, (COUNT != etl::dynamic_extent ? COUNT : Extent - OFFSET)>(pbegin + OFFSET, (pbegin + Extent));
581 }
582 else
583 {
584 return etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : Extent - OFFSET>(pbegin + OFFSET, pbegin + OFFSET + COUNT);
585 }
586 }
587#endif
588
589 //*************************************************************************
591 //*************************************************************************
592 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, etl::dynamic_extent> subspan(size_t offset, size_t count = etl::dynamic_extent) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
593 {
594#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
595 return (offset <= size()) && (count != etl::dynamic_extent ? count <= (size() - offset) : true) ?
596 ((count == etl::dynamic_extent) ? etl::span<element_type, etl::dynamic_extent>(pbegin + offset, (pbegin + Extent))
597 : etl::span<element_type, etl::dynamic_extent>(pbegin + offset, pbegin + offset + count)) :
598 throw(ETL_ERROR(span_out_of_range));
599#else
600 ETL_ASSERT_CHECK_EXTRA(offset <= size(), ETL_ERROR(span_out_of_range));
601 ETL_ASSERT_CHECK_EXTRA(count != etl::dynamic_extent ? count <= (size() - offset) : true, ETL_ERROR(span_out_of_range));
602
603 return (count == etl::dynamic_extent) ? etl::span<element_type, etl::dynamic_extent>(pbegin + offset, (pbegin + Extent))
604 : etl::span<element_type, etl::dynamic_extent>(pbegin + offset, pbegin + offset + count);
605#endif
606 }
607
608 //*************************************************************************
611 //*************************************************************************
612 void advance(size_t elements) ETL_NOEXCEPT
613 {
614 elements = etl::min(elements, size());
615 pbegin += elements;
616 }
617
618 //*************************************************************************
620 //*************************************************************************
621 template<typename TNew>
622 ETL_NODISCARD ETL_CONSTEXPR14 etl::span<TNew, Extent * sizeof(element_type) / sizeof(TNew)> reinterpret_as() const
623 {
625
626 return etl::span<TNew, Extent * sizeof(element_type) / sizeof(TNew)>(reinterpret_cast<TNew*>(pbegin),
627 Extent * sizeof(element_type) / sizeof(TNew));
628 }
629
630 private:
631
632 pointer pbegin;
633 };
634
635 //*************************************************************************
638 //*************************************************************************
639 template <typename T, size_t Extent>
640 ETL_CONSTEXPR span<T, Extent> make_span(T (&data)[Extent])
641 {
642 return span<T, Extent>(data);
643 }
644
645 //***************************************************************************
647 //***************************************************************************
648 template <typename T>
649 class span<T, etl::dynamic_extent> : public span_tag
650 {
651 public:
652
653 typedef T element_type;
654 typedef typename etl::remove_cv<T>::type value_type;
655 typedef size_t size_type;
656 typedef T& reference;
657 typedef const T& const_reference;
658 typedef T* pointer;
659 typedef const T* const_pointer;
660
661 typedef T* iterator;
662 typedef const T* const_iterator;
663 typedef ETL_OR_STD::reverse_iterator<iterator> reverse_iterator;
664 typedef ETL_OR_STD::reverse_iterator<const_iterator> const_reverse_iterator;
665
666 typedef etl::circular_iterator<pointer> circular_iterator;
667 typedef etl::circular_iterator<ETL_OR_STD::reverse_iterator<pointer> > reverse_circular_iterator;
668
669 static ETL_CONSTANT size_t extent = etl::dynamic_extent;
670
671 //*************************************************************************
673 //*************************************************************************
674 ETL_CONSTEXPR span() ETL_NOEXCEPT
675 : pbegin(ETL_NULLPTR)
676 , pend(ETL_NULLPTR)
677 {
678 }
679
680 //*************************************************************************
682 //*************************************************************************
683 template <typename TIterator, typename TSize>
684 ETL_CONSTEXPR span(const TIterator begin_, const TSize size_) ETL_NOEXCEPT
685 : pbegin(etl::to_address(begin_))
686 , pend(etl::to_address(begin_) + size_)
687 {
688 }
689
690 //*************************************************************************
692 //*************************************************************************
693 template <typename TIterator>
694 ETL_CONSTEXPR span(const TIterator begin_, const TIterator end_) ETL_NOEXCEPT
695 : pbegin(etl::to_address(begin_))
696 , pend(etl::to_address(begin_) + etl::distance(begin_, end_))
697 {
698 }
699
700 //*************************************************************************
702 //*************************************************************************
703 template<size_t Array_Size>
704 ETL_CONSTEXPR span(element_type(&begin_)[Array_Size]) ETL_NOEXCEPT
705 : pbegin(begin_)
706 , pend(begin_ + Array_Size)
707 {
708 }
709
710#if ETL_USING_CPP11
711 //*************************************************************************
714 //*************************************************************************
715 template <typename TContainer, typename = typename etl::enable_if<!etl::is_base_of<span_tag, etl::remove_reference_t<TContainer>>::value &&
716 !etl::is_pointer<etl::remove_reference_t<TContainer>>::value &&
717 !etl::is_array<etl::remove_reference_t<TContainer>>::value &&
718 etl::is_same<etl::remove_cv_t<T>, etl::remove_cv_t<typename etl::remove_reference_t<TContainer>::value_type>>::value, void>::type>
719 ETL_CONSTEXPR span(TContainer&& a) ETL_NOEXCEPT
720 : pbegin(a.data())
721 , pend(a.data() + a.size())
722 {
723 }
724#else
725 //*************************************************************************
728 //*************************************************************************
729 template <typename TContainer>
730 ETL_CONSTEXPR span(TContainer& a, typename etl::enable_if<!etl::is_base_of<span_tag, typename etl::remove_reference<TContainer>::type>::value &&
731 !etl::is_pointer<typename etl::remove_reference<TContainer>::type>::value &&
733 etl::is_same<typename etl::remove_cv<T>::type, typename etl::remove_cv<typename etl::remove_reference<TContainer>::type::value_type>::type>::value, void>::type* = 0) ETL_NOEXCEPT
734 : pbegin(a.data())
735 , pend(a.data() + a.size())
736 {
737 }
738
739 //*************************************************************************
742 //*************************************************************************
743 template <typename TContainer>
744 ETL_CONSTEXPR span(const TContainer& a, typename etl::enable_if<!etl::is_base_of<span_tag, typename etl::remove_reference<TContainer>::type>::value &&
745 !etl::is_pointer<typename etl::remove_reference<TContainer>::type>::value &&
747 etl::is_same<typename etl::remove_cv<T>::type, typename etl::remove_cv<typename etl::remove_reference<TContainer>::type::value_type>::type>::value, void>::type* = 0) ETL_NOEXCEPT
748 : pbegin(a.data())
749 , pend(a.data() + a.size())
750 {
751 }
752#endif
753
754 //*************************************************************************
756 //*************************************************************************
757 ETL_CONSTEXPR span(const span& other) ETL_NOEXCEPT
758 : pbegin(other.pbegin)
759 , pend(other.pend)
760 {
761 }
762
763 //*************************************************************************
765 //*************************************************************************
766 template <typename U, size_t Size>
767 ETL_CONSTEXPR span(const etl::span<U, Size>& other) ETL_NOEXCEPT
768 : pbegin(other.data())
769 , pend(other.data() + other.size())
770 {
771 }
772
773 //*************************************************************************
775 //*************************************************************************
776 ETL_NODISCARD ETL_CONSTEXPR reference front() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
777 {
778#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
779 return size() > 0 ? *pbegin : throw(ETL_ERROR(span_out_of_range));
780#else
781 ETL_ASSERT_CHECK_EXTRA(size() > 0, ETL_ERROR(span_out_of_range));
782
783 return *pbegin;
784#endif
785 }
786
787 //*************************************************************************
789 //*************************************************************************
790 ETL_NODISCARD ETL_CONSTEXPR reference back() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
791 {
792#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
793 return size() > 0 ? *(pend - 1) : throw(ETL_ERROR(span_out_of_range));
794#else
795 ETL_ASSERT_CHECK_EXTRA(size() > 0, ETL_ERROR(span_out_of_range));
796
797 return *(pend - 1);
798#endif
799 }
800
801 //*************************************************************************
803 //*************************************************************************
804 ETL_NODISCARD ETL_CONSTEXPR pointer data() const ETL_NOEXCEPT
805 {
806 return pbegin;
807 }
808
809 //*************************************************************************
811 //*************************************************************************
812 ETL_NODISCARD ETL_CONSTEXPR const_iterator cbegin() const ETL_NOEXCEPT
813 {
814 return pbegin;
815 }
816
817 //*************************************************************************
819 //*************************************************************************
820 ETL_NODISCARD ETL_CONSTEXPR iterator begin() const ETL_NOEXCEPT
821 {
822 return pbegin;
823 }
824
825 //*************************************************************************
827 //*************************************************************************
828 ETL_NODISCARD ETL_CONSTEXPR circular_iterator begin_circular() const ETL_NOEXCEPT
829 {
830 return circular_iterator(begin(), end());
831 }
832
833 //*************************************************************************
835 //*************************************************************************
836 ETL_NODISCARD ETL_CONSTEXPR const_iterator cend() const ETL_NOEXCEPT
837 {
838 return pend;
839 }
840
841 //*************************************************************************
843 //*************************************************************************
844 ETL_NODISCARD ETL_CONSTEXPR iterator end() const ETL_NOEXCEPT
845 {
846 return pend;
847 }
848
849 //*************************************************************************
850 // Returns an reverse iterator to the reverse beginning of the span.
851 //*************************************************************************
852 ETL_NODISCARD ETL_CONSTEXPR reverse_iterator rbegin() const ETL_NOEXCEPT
853 {
854 return reverse_iterator(pend);
855 }
856
857 //*************************************************************************
858 // Returns a const reverse iterator to the reverse beginning of the span.
859 //*************************************************************************
860 ETL_NODISCARD ETL_CONSTEXPR const_reverse_iterator crbegin() const ETL_NOEXCEPT
861 {
862 return const_reverse_iterator(pend);
863 }
864
865 //*************************************************************************
867 //*************************************************************************
868 ETL_NODISCARD ETL_CONSTEXPR reverse_circular_iterator rbegin_circular() const ETL_NOEXCEPT
869 {
870 return reverse_circular_iterator(rbegin(), rend());
871 }
872
873 //*************************************************************************
875 //*************************************************************************
876 ETL_NODISCARD ETL_CONSTEXPR const_reverse_iterator crend() const ETL_NOEXCEPT
877 {
878 return const_reverse_iterator(pbegin);
879 }
880
881 //*************************************************************************
883 //*************************************************************************
884 ETL_NODISCARD ETL_CONSTEXPR reverse_iterator rend() const ETL_NOEXCEPT
885 {
886 return reverse_iterator(pbegin);
887 }
888
889 //*************************************************************************
891 //*************************************************************************
892 ETL_NODISCARD ETL_CONSTEXPR bool empty() const ETL_NOEXCEPT
893 {
894 return (pbegin == pend);
895 }
896
897 //*************************************************************************
899 //*************************************************************************
900 ETL_NODISCARD ETL_CONSTEXPR size_t size() const ETL_NOEXCEPT
901 {
902 return (pend - pbegin);
903 }
904
905 //*************************************************************************
907 //*************************************************************************
908 ETL_NODISCARD ETL_CONSTEXPR size_t size_bytes() const ETL_NOEXCEPT
909 {
910 return sizeof(element_type) * (pend - pbegin);
911 }
912
913 //*************************************************************************
915 //*************************************************************************
916 ETL_NODISCARD ETL_CONSTEXPR size_t max_size() const ETL_NOEXCEPT
917 {
918 return size();
919 }
920
921 //*************************************************************************
923 //*************************************************************************
924 ETL_CONSTEXPR14 span& operator =(const span& other) ETL_NOEXCEPT
925 {
926 pbegin = other.pbegin;
927 pend = other.pend;
928 return *this;
929 }
930
931 //*************************************************************************
933 //*************************************************************************
934 ETL_NODISCARD ETL_CONSTEXPR14 reference at(size_t i)
935 {
936 ETL_ASSERT(i < size(), ETL_ERROR(span_out_of_range));
937
938 return pbegin[i];
939 }
940
941 //*************************************************************************
943 //*************************************************************************
944 ETL_NODISCARD ETL_CONSTEXPR14 const_reference at(size_t i) const
945 {
946 ETL_ASSERT(i < size(), ETL_ERROR(span_out_of_range));
947
948 return pbegin[i];
949 }
950
951 //*************************************************************************
953 //*************************************************************************
954 ETL_CONSTEXPR reference operator[](const size_t i) const
955 {
956#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_INDEX_OPERATOR
957 return i < size() ? pbegin[i] : throw(ETL_ERROR(span_out_of_range));
958#else
959 ETL_ASSERT_CHECK_INDEX_OPERATOR(i < size(), ETL_ERROR(span_out_of_range));
960
961 return pbegin[i];
962#endif
963 }
964
965 //*************************************************************************
967 //*************************************************************************
968 template <size_t COUNT>
969 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, COUNT> first() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
970 {
971#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
972 return COUNT <= size() ? etl::span<element_type, COUNT>(pbegin, pbegin + COUNT) : throw(ETL_ERROR(span_out_of_range));
973#else
974 ETL_ASSERT_CHECK_EXTRA(COUNT <= size(), ETL_ERROR(span_out_of_range));
975
976 return etl::span<element_type, COUNT>(pbegin, pbegin + COUNT);
977#endif
978 }
979
980 //*************************************************************************
982 //*************************************************************************
983 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, etl::dynamic_extent> first(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
984 {
985#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
986 return count <= size() ? etl::span<element_type, etl::dynamic_extent>(pbegin, pbegin + count) : throw(ETL_ERROR(span_out_of_range));
987#else
988 ETL_ASSERT_CHECK_EXTRA(count <= size(), ETL_ERROR(span_out_of_range));
989
990 return etl::span<element_type, etl::dynamic_extent>(pbegin, pbegin + count);
991#endif
992 }
993
994 //*************************************************************************
996 //*************************************************************************
997 template <size_t COUNT>
998 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, COUNT> last() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
999 {
1000#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
1001 return COUNT <= size() ? etl::span<element_type, COUNT>(pend - COUNT, pend) : throw(ETL_ERROR(span_out_of_range));
1002#else
1003 ETL_ASSERT_CHECK_EXTRA(COUNT <= size(), ETL_ERROR(span_out_of_range));
1004
1005 return etl::span<element_type, COUNT>(pend - COUNT, pend);
1006#endif
1007 }
1008
1009 //*************************************************************************
1011 //*************************************************************************
1012 ETL_NODISCARD ETL_CONSTEXPR etl::span<element_type, etl::dynamic_extent> last(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
1013 {
1014#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
1015 return count <= size() ? etl::span<element_type, etl::dynamic_extent>(pend - count, pend) : throw(ETL_ERROR(span_out_of_range));
1016#else
1017 ETL_ASSERT_CHECK_EXTRA(count <= size(), ETL_ERROR(span_out_of_range));
1018
1019 return etl::span<element_type, etl::dynamic_extent>(pend - count, pend);
1020#endif
1021 }
1022
1023#if ETL_USING_CPP11
1024 //*************************************************************************
1026 //*************************************************************************
1027 template <size_t OFFSET, size_t COUNT = etl::dynamic_extent>
1028 ETL_NODISCARD ETL_CONSTEXPR
1029 etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : etl::dynamic_extent> subspan() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
1030 {
1031#if ETL_USING_CPP11 && ETL_NOT_USING_CPP14 && ETL_USING_EXCEPTIONS && ETL_CHECKING_EXTRA
1032 return (OFFSET <= size()) && (COUNT != etl::dynamic_extent ? COUNT <= (size() - OFFSET) : true) ?
1033 ((COUNT == etl::dynamic_extent) ? etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : etl::dynamic_extent>(pbegin + OFFSET, pend)
1035 throw(ETL_ERROR(span_out_of_range));
1036#else
1037 ETL_ASSERT_CHECK_EXTRA(OFFSET <= size(), ETL_ERROR(span_out_of_range));
1038 ETL_ASSERT_CHECK_EXTRA(COUNT != etl::dynamic_extent ? COUNT <= (size() - OFFSET) : true, ETL_ERROR(span_out_of_range));
1039
1040 return (COUNT == etl::dynamic_extent) ? etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : etl::dynamic_extent>(pbegin + OFFSET, pend)
1041 : etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : etl::dynamic_extent>(pbegin + OFFSET, pbegin + OFFSET + COUNT);
1042#endif
1043 }
1044#else
1045 //*************************************************************************
1047 //*************************************************************************
1048 template <size_t OFFSET, size_t COUNT>
1050 {
1051 ETL_ASSERT_CHECK_EXTRA(OFFSET <= size(), ETL_ERROR(span_out_of_range));
1052 ETL_ASSERT_CHECK_EXTRA(COUNT != etl::dynamic_extent ? COUNT <= (size() - OFFSET) : true, ETL_ERROR(span_out_of_range));
1053
1054 if (COUNT == etl::dynamic_extent)
1055 {
1057 }
1058 else
1059 {
1060 return etl::span<element_type, COUNT != etl::dynamic_extent ? COUNT : etl::dynamic_extent>(pbegin + OFFSET, pbegin + OFFSET + COUNT);
1061 }
1062 }
1063#endif
1064
1065 //*************************************************************************
1067 //*************************************************************************
1068 ETL_NODISCARD ETL_CONSTEXPR14 etl::span<element_type, etl::dynamic_extent> subspan(size_t offset, size_t count = etl::dynamic_extent) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS || ETL_NOT_CHECKING_EXTRA)
1069 {
1070 ETL_ASSERT_CHECK_EXTRA(offset <= size(), ETL_ERROR(span_out_of_range));
1071 ETL_ASSERT_CHECK_EXTRA(count != etl::dynamic_extent ? count <= (size() - offset) : true, ETL_ERROR(span_out_of_range));
1072
1073 return (count == etl::dynamic_extent) ? etl::span<element_type, etl::dynamic_extent>(pbegin + offset, pend)
1074 : etl::span<element_type, etl::dynamic_extent>(pbegin + offset, pbegin + offset + count);
1075 }
1076
1077 //*************************************************************************
1080 //*************************************************************************
1081 void advance(size_t elements) ETL_NOEXCEPT
1082 {
1083 elements = etl::min(elements, size());
1084 pbegin += elements;
1085 }
1086
1087 //*************************************************************************
1089 //*************************************************************************
1090 template<typename TNew>
1091 ETL_NODISCARD ETL_CONSTEXPR14 etl::span<TNew, etl::dynamic_extent> reinterpret_as() const
1092 {
1094
1095 return etl::span<TNew, etl::dynamic_extent>(reinterpret_cast<TNew*>(pbegin),
1096 (pend - pbegin) * sizeof(element_type) / sizeof(TNew));
1097 }
1098
1099 //*************************************************************************
1104 //*************************************************************************
1105 template<typename TRet>
1106 ETL_NODISCARD etl::span<TRet> take(size_t const n)
1107 {
1108 ETL_STATIC_ASSERT(sizeof(TRet) % sizeof(element_type) == 0, "sizeof(TRet) must be divisible by sizeof(T)");
1109
1111 ETL_ASSERT(sizeof(TRet) * n <= sizeof(element_type) * size(), ETL_ERROR(span_size_mismatch));
1112
1114 advance(sizeof(TRet) / sizeof(element_type) * n);
1115
1116 return result;
1117 }
1118
1119 //*************************************************************************
1123 //*************************************************************************
1124 template<typename TRet>
1125 ETL_NODISCARD TRet& take()
1126 {
1127 ETL_STATIC_ASSERT(sizeof(TRet) % sizeof(element_type) == 0, "sizeof(TRet) must be divisible by sizeof(T)");
1128
1130 ETL_ASSERT(sizeof(TRet) <= sizeof(element_type) * size(), ETL_ERROR(span_size_mismatch));
1131
1132 TRet& result = *reinterpret_cast<TRet*>(data());
1133 advance(sizeof(TRet) / sizeof(element_type));
1134
1135 return result;
1136 }
1137
1138 private:
1139
1140 pointer pbegin;
1141 pointer pend;
1142 };
1143
1144 //*************************************************************************
1147 //*************************************************************************
1148 template <typename T>
1153
1154 //*************************************************************************
1157 //*************************************************************************
1158 template <typename T>
1163
1164 template <typename T, size_t Extent>
1165 ETL_CONSTANT size_t span<T, Extent>::extent;
1166
1167 template <typename T>
1168 ETL_CONSTANT size_t span<T, etl::dynamic_extent>::extent;
1169
1170 //*************************************************************************
1172 //*************************************************************************
1173 template <typename T1, size_t N1, typename T2, size_t N2>
1174 ETL_NODISCARD
1175 ETL_CONSTEXPR
1176 typename etl::enable_if<etl::is_same<typename etl::remove_cv<T1>::type, typename etl::remove_cv<T2>::type>::value, bool>::type
1177 operator ==(const etl::span<T1, N1>& lhs, const etl::span<T2, N2>& rhs) ETL_NOEXCEPT
1178 {
1179 return (lhs.begin() == rhs.begin()) && (lhs.size() == rhs.size());
1180 }
1181
1182 //*************************************************************************
1184 //*************************************************************************
1185 template <typename T1, size_t N1, typename T2, size_t N2>
1186 ETL_NODISCARD
1187 ETL_CONSTEXPR
1188 bool operator !=(const etl::span<T1, N1>& lhs, const etl::span<T2, N2>& rhs) ETL_NOEXCEPT
1189 {
1190 return !(lhs == rhs);
1191 }
1192
1193 //*************************************************************************
1200 //*************************************************************************
1201 template <typename T1, size_t N1, typename T2, size_t N2>
1202 typename etl::enable_if<etl::is_same<typename etl::remove_cv<T1>::type, typename etl::remove_cv<T2>::type>::value, bool>::type
1203 equal(const etl::span<T1, N1>& lhs, const etl::span<T2, N2>& rhs)
1204 {
1205 return (lhs.empty() && rhs.empty()) ||
1206 ((lhs.begin() == rhs.begin()) && (lhs.size() == rhs.size())) ||
1207 etl::equal(lhs.begin(), lhs.end(), rhs.begin(), rhs.end());
1208 }
1209
1210 //*************************************************************************
1219 //*************************************************************************
1220 template <typename T1, size_t N1, typename T2, size_t N2>
1221 typename etl::enable_if<etl::is_same<typename etl::remove_cv<T1>::type, typename etl::remove_cv<T2>::type>::value &&
1222 !etl::is_const<T2>::value, bool>::type
1223 copy(const etl::span<T1, N1>& src, const etl::span<T2, N2>& dst)
1224 {
1225 if (src.empty() || (src.begin() == dst.begin()))
1226 {
1227 return true;
1228 }
1229 if (src.size() > dst.size())
1230 {
1231 return false;
1232 }
1233 (void) etl::copy(src.begin(), src.end(), dst.begin());
1234 return true;
1235 }
1236
1237 //*************************************************************************
1239 //*************************************************************************
1240#if ETL_USING_CPP17
1241 template <typename TIterator>
1242 span(const TIterator begin_, const TIterator end_)
1243 ->span<etl::remove_pointer_t<TIterator>, etl::dynamic_extent>;
1244
1245 template <typename TIterator, typename TSize>
1246 span(const TIterator begin_, const TSize size_)
1247 ->span<etl::remove_pointer_t<TIterator>, etl::dynamic_extent>;
1248
1249 template <typename T, size_t Size>
1250 span(T(&)[Size])
1251 -> span<T, Size>;
1252
1253 template <typename T, size_t Size>
1254 span(etl::array<T, Size>&)
1255 -> span<T, Size>;
1256
1257 template <typename T, size_t Size>
1258 span(const etl::array<T, Size>&)
1259 -> span<const T, Size>;
1260
1261#if ETL_USING_STL && ETL_USING_CPP11
1262 template <typename T, size_t Size>
1263 span(std::array<T, Size>&)
1264 ->span<T, Size>;
1265
1266 template <typename T, size_t Size>
1267 span(const std::array<T, Size>&)
1268 ->span<const T, Size>;
1269#endif
1270#endif
1271
1272 //*************************************************************************
1274 //*************************************************************************
1275#if ETL_USING_8BIT_TYPES
1276 template <typename T, size_t Extent>
1277 struct hash<etl::span<T, Extent> >
1278 {
1279 size_t operator()(const etl::span<T>& view) const
1280 {
1281 return etl::private_hash::generic_hash<size_t>(reinterpret_cast<const uint8_t*>(view.data()),
1282 reinterpret_cast<const uint8_t*>(view.data() + view.size()));
1283 }
1284 };
1285#endif
1286
1287 //*************************************************************************
1289 //*************************************************************************
1290 template <class T, size_t Size>
1291 span<const byte, (Size == etl::dynamic_extent) ? (etl::dynamic_extent) : (Size * sizeof(T))>
1296
1297 //*************************************************************************
1299 //*************************************************************************
1300 template <class T, size_t Size>
1301 span<byte, (Size == etl::dynamic_extent) ? (etl::dynamic_extent) : (Size * sizeof(T))>
1303 {
1304 ETL_STATIC_ASSERT(!etl::is_const<T>::value, "span<T> must be of non-const type");
1306 }
1307}
1308
1309#endif
The byte class.
Definition byte.h:155
Definition iterator.h:228
ETL_NODISCARD ETL_CONSTEXPR circular_iterator begin_circular() const ETL_NOEXCEPT
Returns a circular iterator to the beginning of the span.
Definition span.h:828
ETL_CONSTEXPR span(const TContainer &a, typename etl::enable_if<!etl::is_base_of< span_tag, typename etl::remove_reference< TContainer >::type >::value &&!etl::is_pointer< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_array< TContainer >::value &&etl::is_same< typename etl::remove_cv< T >::type, typename etl::remove_cv< typename etl::remove_reference< TContainer >::type::value_type >::type >::value, void >::type *=0) ETL_NOEXCEPT
Definition span.h:744
ETL_NODISCARD etl::span< TRet > take(size_t const n)
Definition span.h:1106
ETL_CONSTEXPR span(const span &other) ETL_NOEXCEPT
Copy constructor.
Definition span.h:757
ETL_CONSTEXPR span() ETL_NOEXCEPT
Default constructor.
Definition span.h:674
etl::span< element_type, COUNT !=etl::dynamic_extent ? COUNT :etl::dynamic_extent > subspan() const
Obtains a span that is a view from OFFSET over the next COUNT elements of this span.
Definition span.h:1049
void advance(size_t elements) ETL_NOEXCEPT
Definition span.h:1081
ETL_NODISCARD ETL_CONSTEXPR reverse_circular_iterator rbegin_circular() const ETL_NOEXCEPT
Returns a reverse circular iterator to the end of the span.
Definition span.h:868
ETL_NODISCARD ETL_CONSTEXPR14 etl::span< element_type, etl::dynamic_extent > subspan(size_t offset, size_t count=etl::dynamic_extent) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view from 'offset' over the next 'count' elements of this span.
Definition span.h:1068
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, COUNT > last() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view over the last COUNT elements of this span.
Definition span.h:998
ETL_NODISCARD TRet & take()
Definition span.h:1125
ETL_NODISCARD ETL_CONSTEXPR size_t size() const ETL_NOEXCEPT
Returns the size of the span.
Definition span.h:900
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, etl::dynamic_extent > first(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view over the first count elements of this span.
Definition span.h:983
ETL_NODISCARD ETL_CONSTEXPR bool empty() const ETL_NOEXCEPT
Returns true if the span size is zero.
Definition span.h:892
ETL_NODISCARD ETL_CONSTEXPR reference back() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Returns a reference to the last element.
Definition span.h:790
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, etl::dynamic_extent > last(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view over the last count elements of this span.
Definition span.h:1012
ETL_NODISCARD ETL_CONSTEXPR const_reverse_iterator crend() const ETL_NOEXCEPT
Returns a const reverse iterator to the end of the span.
Definition span.h:876
ETL_CONSTEXPR reference operator[](const size_t i) const
Returns a reference to the indexed value.
Definition span.h:954
ETL_CONSTEXPR span(TContainer &a, typename etl::enable_if<!etl::is_base_of< span_tag, typename etl::remove_reference< TContainer >::type >::value &&!etl::is_pointer< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_array< TContainer >::value &&etl::is_same< typename etl::remove_cv< T >::type, typename etl::remove_cv< typename etl::remove_reference< TContainer >::type::value_type >::type >::value, void >::type *=0) ETL_NOEXCEPT
Definition span.h:730
ETL_NODISCARD ETL_CONSTEXPR const_iterator cend() const ETL_NOEXCEPT
Returns a const iterator to the end of the span.
Definition span.h:836
ETL_NODISCARD ETL_CONSTEXPR iterator begin() const ETL_NOEXCEPT
Returns an iterator to the beginning of the span.
Definition span.h:820
ETL_NODISCARD ETL_CONSTEXPR14 const_reference at(size_t i) const
Returns a const reference to the value at index 'i'.
Definition span.h:944
ETL_CONSTEXPR span(const TIterator begin_, const TIterator end_) ETL_NOEXCEPT
Construct from iterators.
Definition span.h:694
ETL_NODISCARD ETL_CONSTEXPR14 etl::span< TNew, etl::dynamic_extent > reinterpret_as() const
Reinterpret the span as a span with different element type.
Definition span.h:1091
ETL_CONSTEXPR span(element_type(&begin_)[Array_Size]) ETL_NOEXCEPT
Construct from C array.
Definition span.h:704
ETL_NODISCARD ETL_CONSTEXPR reference front() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Returns a reference to the first element.
Definition span.h:776
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, COUNT > first() const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view over the first COUNT elements of this span.
Definition span.h:969
ETL_NODISCARD ETL_CONSTEXPR iterator end() const ETL_NOEXCEPT
Returns an iterator to the end of the span.
Definition span.h:844
ETL_NODISCARD ETL_CONSTEXPR const_iterator cbegin() const ETL_NOEXCEPT
Returns a const iterator to the beginning of the span.
Definition span.h:812
ETL_NODISCARD ETL_CONSTEXPR pointer data() const ETL_NOEXCEPT
Returns a pointer to the first element of the internal storage.
Definition span.h:804
ETL_CONSTEXPR span(const TIterator begin_, const TSize size_) ETL_NOEXCEPT
Construct from pointer + size.
Definition span.h:684
ETL_NODISCARD ETL_CONSTEXPR reverse_iterator rend() const ETL_NOEXCEPT
Returns a reverse iterator to the end of the span.
Definition span.h:884
ETL_NODISCARD ETL_CONSTEXPR size_t max_size() const ETL_NOEXCEPT
Returns the maximum possible size of the span.
Definition span.h:916
ETL_NODISCARD ETL_CONSTEXPR size_t size_bytes() const ETL_NOEXCEPT
Returns the size of the span in bytes.
Definition span.h:908
ETL_CONSTEXPR span(const etl::span< U, Size > &other) ETL_NOEXCEPT
Copy constructor.
Definition span.h:767
ETL_NODISCARD ETL_CONSTEXPR14 reference at(size_t i)
Returns a reference to the value at index 'i'.
Definition span.h:934
Definition span.h:75
Span - Fixed Extent.
Definition span.h:138
ETL_NODISCARD ETL_CONSTEXPR reverse_iterator rend() const ETL_NOEXCEPT
Returns a reverse iterator to the end of the span.
Definition span.h:414
ETL_NODISCARD ETL_CONSTEXPR circular_iterator begin_circular() const ETL_NOEXCEPT
Returns a circular iterator to the beginning of the span.
Definition span.h:358
ETL_NODISCARD ETL_CONSTEXPR const_iterator cbegin() const ETL_NOEXCEPT
Returns a const iterator to the beginning of the span.
Definition span.h:342
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, COUNT > last() const ETL_NOEXCEPT
Obtains a span that is a view over the last COUNT elements of this span.
Definition span.h:524
ETL_CONSTEXPR span(etl::array< U, Size > &other, typename etl::enable_if< Size==Extent, void >::type *=0) ETL_NOEXCEPT
Constructor from etl array.
Definition span.h:297
ETL_CONSTEXPR span(const span &other) ETL_NOEXCEPT
Copy constructor.
Definition span.h:247
etl::span< element_type, COUNT !=etl::dynamic_extent ? COUNT :Extent - OFFSET > subspan() const
Obtains a span that is a view from OFFSET over the next COUNT elements of this span.
Definition span.h:570
void advance(size_t elements) ETL_NOEXCEPT
Definition span.h:612
ETL_NODISCARD ETL_CONSTEXPR reverse_circular_iterator rbegin_circular() const ETL_NOEXCEPT
Returns a reverse circular iterator to the end of the span.
Definition span.h:398
ETL_CONSTEXPR span(const etl::array< U, Size > &other, typename etl::enable_if< Size==Extent &&etl::is_const< T >::value, void >::type *=0) ETL_NOEXCEPT
Constructor from const etl array.
Definition span.h:306
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, etl::dynamic_extent > last(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view over the last count elements of this span.
Definition span.h:535
ETL_NODISCARD ETL_CONSTEXPR iterator begin() const ETL_NOEXCEPT
Returns an iterator to the beginning of the span.
Definition span.h:350
ETL_NODISCARD ETL_CONSTEXPR size_t size_bytes() const ETL_NOEXCEPT
Returns the size of the span in bytes.
Definition span.h:438
span(TContainer &a, typename etl::enable_if<!etl::is_base_of< span_tag, typename etl::remove_reference< TContainer >::type >::value &&!etl::is_std_array< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_etl_array< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_pointer< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_array< TContainer >::value &&etl::is_same< typename etl::remove_cv< T >::type, typename etl::remove_cv< typename etl::remove_reference< TContainer >::type::value_type >::type >::value, void >::type *=0) ETL_NOEXCEPT
Definition span.h:218
span(const TContainer &a, typename etl::enable_if<!etl::is_base_of< span_tag, typename etl::remove_reference< TContainer >::type >::value &&!etl::is_std_array< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_etl_array< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_pointer< typename etl::remove_reference< TContainer >::type >::value &&!etl::is_array< TContainer >::value &&etl::is_same< typename etl::remove_cv< T >::type, typename etl::remove_cv< typename etl::remove_reference< TContainer >::type::value_type >::type >::value, void >::type *=0) ETL_NOEXCEPT
Definition span.h:233
ETL_NODISCARD ETL_CONSTEXPR bool empty() const ETL_NOEXCEPT
Returns true if the span size is zero.
Definition span.h:422
ETL_NODISCARD ETL_CONSTEXPR const_iterator cend() const ETL_NOEXCEPT
Returns a const iterator to the end of the span.
Definition span.h:366
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, COUNT > first() const ETL_NOEXCEPT
Obtains a span that is a view over the first COUNT elements of this span.
Definition span.h:498
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, etl::dynamic_extent > subspan(size_t offset, size_t count=etl::dynamic_extent) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view from 'offset' over the next 'count' elements of this span.
Definition span.h:592
ETL_NODISCARD ETL_CONSTEXPR size_t size() const ETL_NOEXCEPT
Returns the size of the span.
Definition span.h:430
ETL_NODISCARD ETL_CONSTEXPR reference back() const ETL_NOEXCEPT
Returns a reference to the last element.
Definition span.h:324
ETL_CONSTEXPR14 span & operator=(const span &other) ETL_NOEXCEPT
Assign from a span.
Definition span.h:454
ETL_CONSTEXPR14 span(const etl::span< U, Size > &other, typename etl::enable_if< Size==etl::dynamic_extent, void >::type *=0)
Definition span.h:267
ETL_NODISCARD ETL_CONSTEXPR14 etl::span< TNew, Extent *sizeof(element_type)/sizeof(TNew)> reinterpret_as() const
Reinterpret the span as a span with different element type.
Definition span.h:622
ETL_NODISCARD ETL_CONSTEXPR etl::span< element_type, etl::dynamic_extent > first(size_t count) const ETL_NOEXCEPT_EXPR(ETL_NOT_USING_EXCEPTIONS||ETL_NOT_CHECKING_EXTRA)
Obtains a span that is a view over the first count elements of this span.
Definition span.h:509
ETL_CONSTEXPR span(const TIterator begin_, const TIterator) ETL_NOEXCEPT
Construct from iterators.
Definition span.h:172
ETL_NODISCARD ETL_CONSTEXPR pointer data() const ETL_NOEXCEPT
Definition span.h:334
ETL_CONSTEXPR span(const etl::span< U, Size > &other, typename etl::enable_if< Size==Extent, void >::type *=0) ETL_NOEXCEPT
Definition span.h:257
ETL_CONSTEXPR span(const TIterator begin_, const TSize) ETL_NOEXCEPT
Construct from iterators + size.
Definition span.h:163
ETL_NODISCARD ETL_CONSTEXPR14 reference at(size_t i)
Returns a reference to the value at index 'i'.
Definition span.h:463
ETL_CONSTEXPR reference operator[](const size_t i) const
Returns a reference to the indexed value.
Definition span.h:483
ETL_NODISCARD ETL_CONSTEXPR14 const_reference at(size_t i) const
Returns a const reference to the value at index 'i'.
Definition span.h:473
ETL_NODISCARD ETL_CONSTEXPR const_reverse_iterator crend() const ETL_NOEXCEPT
Returns a const reverse iterator to the end of the span.
Definition span.h:406
ETL_NODISCARD ETL_CONSTEXPR size_t max_size() const ETL_NOEXCEPT
Returns the maximum possible size of the span.
Definition span.h:446
ETL_NODISCARD ETL_CONSTEXPR reference front() const ETL_NOEXCEPT
Returns a reference to the first element.
Definition span.h:314
ETL_NODISCARD ETL_CONSTEXPR iterator end() const ETL_NOEXCEPT
Returns an iterator to the end of the span.
Definition span.h:374
ETL_CONSTEXPR span(element_type(&begin_)[Array_Size], typename etl::enable_if<(Array_Size==Extent), void >::type *=0) ETL_NOEXCEPT
Construct from C array.
Definition span.h:191
Definition array.h:88
#define ETL_ASSERT(b, e)
Definition error_handler.h:356
ETL_CONSTEXPR exception(string_type reason_, string_type, numeric_type line_)
Constructor.
Definition exception.h:69
Definition span.h:96
Definition span.h:124
Definition span.h:110
integral_constant< bool, false > false_type
integral_constant specialisations
Definition type_traits_generator.h:899
add_rvalue_reference
Definition type_traits_generator.h:1413
enable_if
Definition type_traits_generator.h:1254
is_array
Definition type_traits_generator.h:1154
is_base_of
Definition type_traits_generator.h:1315
is_pointer
Definition type_traits_generator.h:1164
is_same
Definition type_traits_generator.h:1104
remove_cv
Definition type_traits_generator.h:1031
remove_reference
Definition type_traits_generator.h:941
bitset_ext
Definition absolute.h:39
ETL_CONSTEXPR TContainer::const_reverse_iterator crbegin(const TContainer &container)
Definition iterator.h:1104
ETL_CONSTEXPR TContainer::reverse_iterator rbegin(TContainer &container)
Definition iterator.h:1084
bool is_aligned(const void *p, size_t required_alignment)
Check that 'p' has 'required_alignment'.
Definition alignment.h:92
bool operator!=(const etl::array< T, SIZE > &lhs, const etl::array< T, SIZE > &rhs)
Definition array.h:1151
span< const byte,(Size==etl::dynamic_extent) ?(etl::dynamic_extent) :(Size *sizeof(T))> as_bytes(span< T, Size > s) ETL_NOEXCEPT
Template deduction guides.
Definition span.h:1292
ETL_CONSTEXPR T * to_address(T *p) ETL_NOEXCEPT
Definition memory.h:62
span< byte,(Size==etl::dynamic_extent) ?(etl::dynamic_extent) :(Size *sizeof(T))> as_writable_bytes(span< T, Size > s) ETL_NOEXCEPT
Obtains a view to the byte representation of the elements of the span s.
Definition span.h:1302
bool operator==(const etl::array< T, SIZE > &lhs, const etl::array< T, SIZE > &rhs)
Definition array.h:1139
ETL_CONSTEXPR span< T, Extent > make_span(T(&data)[Extent])
Definition span.h:640
Definition span.h:66
Definition span.h:58