File indexing completed on 2025-01-18 09:54:52
0001
0002
0003
0004
0005 #ifndef CPPCORO_SEQUENCE_RANGE_HPP_INCLUDED
0006 #define CPPCORO_SEQUENCE_RANGE_HPP_INCLUDED
0007
0008 #include <cppcoro/sequence_traits.hpp>
0009
0010 #include <algorithm>
0011 #include <iterator>
0012
0013 namespace cppcoro
0014 {
0015 template<typename SEQUENCE, typename TRAITS = sequence_traits<SEQUENCE>>
0016 class sequence_range
0017 {
0018 public:
0019
0020 using value_type = SEQUENCE;
0021 using difference_type = typename TRAITS::difference_type;
0022 using size_type = typename TRAITS::size_type;
0023
0024 class const_iterator
0025 {
0026 public:
0027
0028 using iterator_category = std::random_access_iterator_tag;
0029 using value_type = SEQUENCE;
0030 using difference_type = typename TRAITS::difference_type;
0031 using reference = const SEQUENCE&;
0032 using pointer = const SEQUENCE*;
0033
0034 explicit constexpr const_iterator(SEQUENCE value) noexcept : m_value(value) {}
0035
0036 const SEQUENCE& operator*() const noexcept { return m_value; }
0037 const SEQUENCE* operator->() const noexcept { return std::addressof(m_value); }
0038
0039 const_iterator& operator++() noexcept { ++m_value; return *this; }
0040 const_iterator& operator--() noexcept { --m_value; return *this; }
0041
0042 const_iterator operator++(int) noexcept { return const_iterator(m_value++); }
0043 const_iterator operator--(int) noexcept { return const_iterator(m_value--); }
0044
0045 constexpr difference_type operator-(const_iterator other) const noexcept { return TRAITS::difference(m_value, other.m_value); }
0046 constexpr const_iterator operator-(difference_type delta) const noexcept { return const_iterator{ static_cast<SEQUENCE>(m_value - delta) }; }
0047 constexpr const_iterator operator+(difference_type delta) const noexcept { return const_iterator{ static_cast<SEQUENCE>(m_value + delta) }; }
0048
0049 constexpr bool operator==(const_iterator other) const noexcept { return m_value == other.m_value; }
0050 constexpr bool operator!=(const_iterator other) const noexcept { return m_value != other.m_value; }
0051
0052 private:
0053
0054 SEQUENCE m_value;
0055
0056 };
0057
0058 constexpr sequence_range() noexcept
0059 : m_begin()
0060 , m_end()
0061 {}
0062
0063 constexpr sequence_range(SEQUENCE begin, SEQUENCE end) noexcept
0064 : m_begin(begin)
0065 , m_end(end)
0066 {}
0067
0068 constexpr const_iterator begin() const noexcept { return const_iterator(m_begin); }
0069 constexpr const_iterator end() const noexcept { return const_iterator(m_end); }
0070
0071 constexpr SEQUENCE front() const noexcept { return m_begin; }
0072 constexpr SEQUENCE back() const noexcept { return m_end - 1; }
0073
0074 constexpr size_type size() const noexcept
0075 {
0076 return static_cast<size_type>(TRAITS::difference(m_end, m_begin));
0077 }
0078
0079 constexpr bool empty() const noexcept
0080 {
0081 return m_begin == m_end;
0082 }
0083
0084 constexpr SEQUENCE operator[](size_type index) const noexcept
0085 {
0086 return m_begin + index;
0087 }
0088
0089 constexpr sequence_range first(size_type count) const noexcept
0090 {
0091 return sequence_range{ m_begin, static_cast<SEQUENCE>(m_begin + std::min(size(), count)) };
0092 }
0093
0094 constexpr sequence_range skip(size_type count) const noexcept
0095 {
0096 return sequence_range{ m_begin + std::min(size(), count), m_end };
0097 }
0098
0099 private:
0100
0101 SEQUENCE m_begin;
0102 SEQUENCE m_end;
0103
0104 };
0105 }
0106
0107 #endif