OpenKalman
range-concepts.hpp
Go to the documentation of this file.
1 /* This file is part of OpenKalman, a header-only C++ library for
2  * Kalman filters and other recursive filters.
3  *
4  * Copyright (c) 2025 Christopher Lee Ogden <ogden@gatech.edu>
5  *
6  * This Source Code Form is subject to the terms of the Mozilla Public
7  * License, v. 2.0. If a copy of the MPL was not distributed with this
8  * file, You can obtain one at https://mozilla.org/MPL/2.0/.
9  */
10 
21 #ifndef OPENKALMAN_RANGES_RANGE_CONCEPTS_HPP
22 #define OPENKALMAN_RANGES_RANGE_CONCEPTS_HPP
23 
24 #ifndef __cpp_lib_ranges
25 
28 #include "range-access.hpp"
29 
30 namespace OpenKalman::ranges
31 {
32  // ---
33  // range
34  // ---
35 
36  namespace detail
37  {
38  template<typename T, typename = void>
39  struct is_range : std::false_type {};
40 
41  template<typename T>
42  struct is_range<T, std::void_t<iterator_t<T>, sentinel_t<T>>> : std::true_type {};
43  }
44 
45 
46  template<typename T>
47  inline constexpr bool range = detail::is_range<T>::value;
48 
49 
50  // ---
51  // borrowed_range
52  // ---
53 
54  namespace detail_borrowed_range
55  {
56 #ifdef __cpp_lib_remove_cvref
57  using std::remove_cvref_t;
58 #endif
59 
60 
61  template<typename R, typename = void>
62  struct is_borrowed_range : std::false_type {};
63 
64  template<typename R>
65  struct is_borrowed_range<R, std::enable_if_t<range<R> and
66  (std::is_lvalue_reference_v<R> or enable_borrowed_range<remove_cvref_t<R>>)>> : std::true_type {};
67  }
68 
69  template<typename T>
70  inline constexpr bool borrowed_range = detail_borrowed_range::is_borrowed_range<T>::value;
71 
72 
73  // ---
74  // sized_range
75  // ---
76 
77  namespace detail
78  {
79  template<typename T, typename = void>
80  struct is_sized_range : std::false_type {};
81 
82  template<typename T>
83  struct is_sized_range<T, std::void_t<decltype(ranges::size(std::declval<T&>()))>> : std::true_type {};
84 
85  }
86 
87  template<typename T>
88  inline constexpr bool sized_range = range<T> and detail::is_sized_range<T>::value;
89 
90 
91  // ---
92  // input_range
93  // ---
94 
95  namespace detail
96  {
97  template<typename T, typename = void>
98  struct has_input_iterator : std::false_type {};
99 
100  template<typename T>
101  struct has_input_iterator<T, std::enable_if_t<input_iterator<iterator_t<T>>>> : std::true_type {};
102  }
103 
104 
105  template<typename T>
106  inline constexpr bool input_range = range<T> and detail::has_input_iterator<T>::value;
107 
108 
109  // ---
110  // output_range
111  // ---
112 
113  namespace detail
114  {
115  template<typename R, typename T, typename = void>
116  struct has_output_iterator : std::false_type {};
117 
118  template<typename R, typename T>
119  struct has_output_iterator<R, T, std::enable_if_t<output_iterator<iterator_t<R>, T>>> : std::true_type {};
120  }
121 
122 
123  template<typename R, typename T>
124  inline constexpr bool output_range = range<R> and detail::has_output_iterator<R, T>::value;
125 
126 
127  // ---
128  // forward_range
129  // ---
130 
131  namespace detail
132  {
133  template<typename T, typename = void>
134  struct has_forward_iterator : std::false_type {};
135 
136  template<typename T>
137  struct has_forward_iterator<T, std::enable_if_t<forward_iterator<iterator_t<T>>>> : std::true_type {};
138  }
139 
140 
141  template<typename T>
142  inline constexpr bool forward_range = input_range<T> and detail::has_forward_iterator<T>::value;
143 
144 
145  // ---
146  // bidirectional_range
147  // ---
148 
149  namespace detail
150  {
151  template<typename T, typename = void>
152  struct has_bidirectional_iterator : std::false_type {};
153 
154  template<typename T>
155  struct has_bidirectional_iterator<T, std::enable_if_t<bidirectional_iterator<iterator_t<T>>>> : std::true_type {};
156  }
157 
158 
159  template<typename T>
160  inline constexpr bool bidirectional_range = forward_range<T> and detail::has_bidirectional_iterator<T>::value;
161 
162 
163  // ---
164  // random_access_range
165  // ---
166 
167  namespace detail
168  {
169  template<typename T, typename = void>
170  struct has_random_access_iterator : std::false_type {};
171 
172  template<typename T>
173  struct has_random_access_iterator<T, std::enable_if_t<random_access_iterator<iterator_t<T>>>> : std::true_type {};
174  }
175 
176 
177  template<typename T>
178  inline constexpr bool random_access_range = bidirectional_range<T> and detail::has_random_access_iterator<T>::value;
179 
180 
181  // ---
182  // common_range
183  // ---
184 
185  namespace detail
186  {
187  template<typename T, typename = void>
188  struct is_common_range : std::false_type {};
189 
190  template<typename T>
191  struct is_common_range<T, std::enable_if_t<std::is_same_v<iterator_t<T>, sentinel_t<T>>>> : std::true_type {};
192  }
193 
194 
195  template<typename T>
196  inline constexpr bool common_range = range<T> and detail::is_common_range<T>::value;
197 
198 
199 
200  // ---
201  // Range primitives
202  // ---
203 
204  template<typename R, std::enable_if_t<sized_range<R>, int> = 0>
205  using range_size_t = decltype(size(std::declval<R&>()));
206 
207  template<typename R, std::enable_if_t<range<R>, int> = 0>
208  using range_difference_t = iter_difference_t<iterator_t<R>>;
209 
210  template<typename R, std::enable_if_t<range<R>, int> = 0>
211  using range_value_t = iter_value_t<iterator_t<R>>;
212 
213 
214  template<typename R, std::enable_if_t<range<R>, int> = 0>
215  using range_reference_t = iter_reference_t<iterator_t<R>>;
216 
217  template<typename R, std::enable_if_t<range<R>, int> = 0>
218  using range_const_reference_t = iter_const_reference_t<iterator_t<R>>;
219 
220  template<typename R, std::enable_if_t<range<R>, int> = 0>
221  using range_rvalue_reference_t = iter_rvalue_reference_t<iterator_t<R>>;
222 
223  template<typename R, std::enable_if_t<range<R>, int> = 0>
224  using range_common_reference_t = iter_common_reference_t<iterator_t<R>>;
225 
226 } // namespace OpenKalman::ranges
227 
228 #endif
229 
230 
231 #endif //OPENKALMAN_RANGES_RANGE_CONCEPTS_HPP
Definition: range-concepts.hpp:188
Definition: range-concepts.hpp:80
Definition: tuple_reverse.hpp:103
Definition: range-access.hpp:25
Definition: range-concepts.hpp:98
Definitions relating to the availability of c++ language features.
Definition: range-concepts.hpp:39
constexpr bool size
T is either an index representing a size, or void which represents that there is no size...
Definition: size.hpp:32
Definition: range-concepts.hpp:116
Definition: range-concepts.hpp:134