MCRO
C++23 utilities for Unreal Engine.
All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages Concepts
Concepts.h
Go to the documentation of this file.
1/** @noop License Comment
2 * @file
3 * @copyright
4 * This Source Code is subject to the terms of the Mozilla Public License, v2.0.
5 * If a copy of the MPL was not distributed with this file You can obtain one at
6 * https://mozilla.org/MPL/2.0/
7 *
8 * @author David Mórász
9 * @date 2025
10 */
11
12#pragma once
13
14#include "CoreMinimal.h"
15
16#include "Mcro/Concepts.h"
17
19#include "range/v3/all.hpp"
21
22namespace Mcro::Range
23{
24 using namespace Mcro::Concepts;
25
27 {
29 Forward,
31 };
32 enum class EIteratorStep
33 {
35 Single,
36 Jump,
38 };
39
40 template <typename L, typename R>
41 concept CHasEquals = requires (L& a, R& b) { a == b; };
42
43 template <typename L, typename R>
44 concept CHasNotEquals = requires (L& a, R& b) { a != b; };
45
46 template <typename L, typename R>
47 bool IteratorEquals(L const& l, R const& r)
48 {
49 if constexpr (CHasEquals<L, R>)
50 return l == r;
51 else return !(l != r);
52 }
53
54 /** @brief The most basic minimal iterator which can only proceed forward one element at a time */
55 template <typename T>
56 concept CBasicForwardIteratorBase = CPointer<T> || requires(T& i) { ++i; *i; };
57
58 template <typename T>
61 ;
62
63 template <typename T>
64 concept CHasMemberAccessOperator = requires(T& i) { i.operator->(); };
65
66 /** @brief Basic minimal iterator which can only proceed forward or backward one element at a time */
67 template <typename T>
68 concept CBasicBidirectionalIterator = CPointer<T> || (CBasicForwardIterator<T> && requires(T& i) { --i; });
69
70 /** @brief An iterator type which can natively proceed forward in arbitrarily large steps */
71 template <typename T>
72 concept CJumpForwardIterator = CPointer<T> || (CBasicForwardIterator<T> && requires(T& i) { i += 2; });
73
74 /** @brief An iterator type which can natively proceed forward in arbitrarily large steps and exposes a + operator */
75 template <typename T>
76 concept CJumpForwardPlusIterator = CPointer<T> || (CJumpForwardIterator<T> && requires(T& i) { { i + 2 } -> CConvertibleToDecayed<T>; });
77
78 /** @brief An iterator type which can natively seek its associated content in arbitrarily large steps */
79 template <typename T>
80 concept CRandomAccessIterator = CPointer<T> || (CJumpForwardIterator<T> && requires(T& i) { i -= 2; });
81
82 /**
83 * @brief
84 * An iterator type which can natively seek its associated content in arbitrarily large steps and exposes +- operators
85 */
86 template <typename T>
87 concept CRandomAccessPlusMinusIterator = CPointer<T> ||
88 (
91 && requires(T& i)
92 {
93 { i - 2 } -> CConvertibleToDecayed<T>;
94 }
95 );
96
97 /** @brief Get the direction given iterator is capable of */
98 template <typename T>
105 ;
106
107 /** @brief Get the maximum steps the given iterator can be seeking with */
108 template <typename T>
117 ;
118
119 /** @brief Assume an STL iterator category from input iterator */
120 template <typename T>
121 using TIteratorCategory = std::conditional_t<
123 std::random_access_iterator_tag,
124 std::conditional_t<
126 std::bidirectional_iterator_tag,
127 std::conditional_t<
129 std::forward_iterator_tag,
130 std::input_iterator_tag
131 >
132 >
133 >;
134
135 /**
136 * @brief
137 * Constraint given iterator to its best stepping capability.
138 *
139 * To constrain for "at least" method of capability use `CBasicForwardIterator` and refining concepts.
140 */
141 template <typename T, EIteratorStep Step>
143
144 /**
145 * @brief
146 * Constraint given iterator to its best directional capability.
147 *
148 * To constrain for "at least" method of capability use `CBasicForwardIterator` and refining concepts.
149 */
150 template <typename T, EIteratorDirection Direction>
152
153 /** @brief Constraint given iterator to its best capabilies both in stepping and in direction */
154 template <typename T, EIteratorDirection Direction, EIteratorStep Step>
156
157 /** @brief return the iterator's associated content type when they're dereferenced. */
158 template <CBasicForwardIterator T>
159 using TIteratorElementType = std::decay_t<decltype(*DeclVal<T>())>;
160
161 /** @brief return a range's associated content type determined by dereferencing their iterator. */
162 template <CRangeMember T>
164
165 template <typename T>
166 concept CUnrealRange = CRangeMember<T>
167 && requires(T& container, TRangeElementType<T> const& item)
168 {
169 container.Add(item);
170 };
171
172 template <typename T>
173 concept CStdDistanceCompatible = requires(T& l, T& r) { std::distance(l, r); };
174
175 template <typename T>
176 concept CHasGetIndex = requires(T& i) { i.GetIndex(); };
177
178 template <typename T>
179 concept CHasElementIndex = requires(T& i) { i.ElementIndex; };
180
181 template <typename T>
183 CTotallyOrdered<T>
186 ;
187
188 template <typename T>
189 concept CCountableRange = requires(T&& t) { size(t); };
190}
This header exists because STL headers in Android doesn't define STL concepts (other than same_as whi...
Use this header and Start.h in tandem to include third-party library headers which may not tolerate U...
size_t size(TArray< T, A > const &r)
Definition Range.h:98
Use this header and End.h in tandem to include third-party library headers which may not tolerate Unr...
Basic minimal iterator which can only proceed forward or backward one element at a time.
Definition Concepts.h:68
The most basic minimal iterator which can only proceed forward one element at a time.
Definition Concepts.h:56
Constraint given iterator to its best directional capability.
Definition Concepts.h:151
Constraint given iterator to its best stepping capability.
Definition Concepts.h:142
Constraint given iterator to its best capabilies both in stepping and in direction.
Definition Concepts.h:155
An iterator type which can natively proceed forward in arbitrarily large steps.
Definition Concepts.h:72
An iterator type which can natively proceed forward in arbitrarily large steps and exposes a + operat...
Definition Concepts.h:76
An iterator type which can natively seek its associated content in arbitrarily large steps.
Definition Concepts.h:80
An iterator type which can natively seek its associated content in arbitrarily large steps and expose...
Definition Concepts.h:87
constexpr EIteratorStep TIteratorStep
Get the maximum steps the given iterator can be seeking with.
Definition Concepts.h:109
std::decay_t< decltype(*DeclVal< T >())> TIteratorElementType
return the iterator's associated content type when they're dereferenced.
Definition Concepts.h:159
constexpr EIteratorDirection TIteratorDirection
Get the direction given iterator is capable of.
Definition Concepts.h:99
bool IteratorEquals(L const &l, R const &r)
Definition Concepts.h:47
TIteratorElementType< decltype(DeclVal< T >().begin())> TRangeElementType
return a range's associated content type determined by dereferencing their iterator.
Definition Concepts.h:163
std::conditional_t< CRandomAccessIterator< T >, std::random_access_iterator_tag, std::conditional_t< CBasicBidirectionalIterator< T >, std::bidirectional_iterator_tag, std::conditional_t< CBasicForwardIterator< T >, std::forward_iterator_tag, std::input_iterator_tag > > > TIteratorCategory
Assume an STL iterator category from input iterator.
Definition Concepts.h:121