• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //===-- Standalone implementation of iterator -------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #ifndef LLVM_LIBC_SRC___SUPPORT_CPP_ITERATOR_H
10 #define LLVM_LIBC_SRC___SUPPORT_CPP_ITERATOR_H
11 
12 #include "src/__support/CPP/type_traits/enable_if.h"
13 #include "src/__support/CPP/type_traits/is_convertible.h"
14 #include "src/__support/CPP/type_traits/is_same.h"
15 #include "src/__support/macros/attributes.h"
16 
17 namespace LIBC_NAMESPACE {
18 namespace cpp {
19 
20 template <typename T> struct iterator_traits;
21 template <typename T> struct iterator_traits<T *> {
22   using reference = T &;
23   using value_type = T;
24 };
25 
26 template <typename Iter> class reverse_iterator {
27   Iter current;
28 
29 public:
30   using reference = typename iterator_traits<Iter>::reference;
31   using value_type = typename iterator_traits<Iter>::value_type;
32   using iterator_type = Iter;
33 
34   LIBC_INLINE reverse_iterator() : current() {}
35   LIBC_INLINE constexpr explicit reverse_iterator(Iter it) : current(it) {}
36 
37   template <typename Other,
38             cpp::enable_if_t<!cpp::is_same_v<Iter, Other> &&
39                                  cpp::is_convertible_v<const Other &, Iter>,
40                              int> = 0>
41   LIBC_INLINE constexpr explicit reverse_iterator(const Other &it)
42       : current(it) {}
43 
44   LIBC_INLINE friend constexpr bool operator==(const reverse_iterator &lhs,
45                                                const reverse_iterator &rhs) {
46     return lhs.base() == rhs.base();
47   }
48 
49   LIBC_INLINE friend constexpr bool operator!=(const reverse_iterator &lhs,
50                                                const reverse_iterator &rhs) {
51     return lhs.base() != rhs.base();
52   }
53 
54   LIBC_INLINE friend constexpr bool operator<(const reverse_iterator &lhs,
55                                               const reverse_iterator &rhs) {
56     return lhs.base() > rhs.base();
57   }
58 
59   LIBC_INLINE friend constexpr bool operator<=(const reverse_iterator &lhs,
60                                                const reverse_iterator &rhs) {
61     return lhs.base() >= rhs.base();
62   }
63 
64   LIBC_INLINE friend constexpr bool operator>(const reverse_iterator &lhs,
65                                               const reverse_iterator &rhs) {
66     return lhs.base() < rhs.base();
67   }
68 
69   LIBC_INLINE friend constexpr bool operator>=(const reverse_iterator &lhs,
70                                                const reverse_iterator &rhs) {
71     return lhs.base() <= rhs.base();
72   }
73 
74   LIBC_INLINE constexpr iterator_type base() const { return current; }
75 
76   LIBC_INLINE constexpr reference operator*() const {
77     Iter tmp = current;
78     return *--tmp;
79   }
80   LIBC_INLINE constexpr reverse_iterator operator--() {
81     ++current;
82     return *this;
83   }
84   LIBC_INLINE constexpr reverse_iterator &operator++() {
85     --current;
86     return *this;
87   }
88   LIBC_INLINE constexpr reverse_iterator operator++(int) {
89     reverse_iterator tmp(*this);
90     --current;
91     return tmp;
92   }
93 };
94 
95 } // namespace cpp
96 } // namespace LIBC_NAMESPACE
97 
98 #endif // LLVM_LIBC_SRC___SUPPORT_CPP_ITERATOR_H
99