Algorithms Library Toolkit
A toolkit for algorithms, especially for algorithms on formal languages
All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Concepts
OperatorRegistry.hpp
Go to the documentation of this file.
1
6#pragma once
7
8#include <ext/functional>
9#include <ext/memory>
10#include <ext/vector>
11#include <ext/list>
12#include <ext/string>
13#include <ext/set>
14#include <ext/map>
15#include <ext/typeinfo>
16
18
21#include <common/Operators.hpp>
22
24#include "BaseRegistryEntry.hpp"
25
26namespace abstraction {
27
29public:
31 AlgorithmFullInfo m_entryInfo;
32
33 public:
34 explicit BinaryEntry ( AlgorithmFullInfo entryInfo ) : m_entryInfo ( std::move ( entryInfo ) ) {
35 }
36
37 const AlgorithmFullInfo & getEntryInfo ( ) const {
38 return m_entryInfo;
39 }
40 };
41
43 AlgorithmFullInfo m_entryInfo;
44
45 public:
46 explicit PrefixEntry ( AlgorithmFullInfo entryInfo ) : m_entryInfo ( std::move ( entryInfo ) ) {
47 }
48
49 const AlgorithmFullInfo & getEntryInfo ( ) const {
50 return m_entryInfo;
51 }
52 };
53
55 AlgorithmFullInfo m_entryInfo;
56
57 public:
58 explicit PostfixEntry ( AlgorithmFullInfo entryInfo ) : m_entryInfo ( std::move ( entryInfo ) ) {
59 }
60
61 const AlgorithmFullInfo & getEntryInfo ( ) const {
62 return m_entryInfo;
63 }
64 };
65
66private:
67 template < class Return, class FirstParam, class SecondParam >
68 class BinaryOperator : public BinaryEntry {
69 std::function < Return ( FirstParam, SecondParam ) > m_callback;
70
71 public:
72 explicit BinaryOperator ( std::function < Return ( FirstParam, SecondParam ) > callback ) : BinaryEntry ( AlgorithmFullInfo::operatorEntryInfo < Return, FirstParam, SecondParam > ( ) ), m_callback ( std::move ( callback ) ) {
73 }
74
75 std::shared_ptr < abstraction::OperationAbstraction > getAbstraction ( ) const override;
76 };
77
78 template < class Return, class Param >
79 class PrefixOperator : public PrefixEntry {
80 std::function < Return ( Param ) > m_callback;
81
82 public:
83 explicit PrefixOperator ( std::function < Return ( Param ) > callback ) : PrefixEntry ( AlgorithmFullInfo::operatorEntryInfo < Return, Param > ( ) ), m_callback ( std::move ( callback ) ) {
84 }
85
86 std::shared_ptr < abstraction::OperationAbstraction > getAbstraction ( ) const override;
87 };
88
89 template < class Return, class Param >
90 class PostfixOperator : public PostfixEntry {
91 std::function < Return ( Param ) > m_callback;
92
93 public:
94 explicit PostfixOperator ( std::function < Return ( Param ) > callback ) : PostfixEntry ( AlgorithmFullInfo::operatorEntryInfo < Return, Param > ( ) ), m_callback ( std::move ( callback ) ) {
95 }
96
97 std::shared_ptr < abstraction::OperationAbstraction > getAbstraction ( ) const override;
98 };
99
101
102 static bool isRegisteredBinary ( Operators::BinaryOperators type, const AlgorithmBaseInfo & entryInfo );
103
104 static void registerBinaryInternal ( Operators::BinaryOperators type, std::unique_ptr < BinaryEntry > value );
105
106 static void unregisterBinaryInternal ( Operators::BinaryOperators type, const AlgorithmBaseInfo & entryInfo );
107
108
109
111
112 static bool isRegisteredPrefix ( Operators::PrefixOperators type, const AlgorithmBaseInfo & entryInfo );
113
114 static void registerPrefixInternal ( Operators::PrefixOperators type, std::unique_ptr < PrefixEntry > value );
115
116 static void unregisterPrefixInternal ( Operators::PrefixOperators type, const AlgorithmBaseInfo & entryInfo );
117
118
119
121
122 static bool isRegisteredPostfix ( Operators::PostfixOperators type, const AlgorithmBaseInfo & entryInfo );
123
124 static void registerPostfixInternal ( Operators::PostfixOperators type, std::unique_ptr < PostfixEntry > value );
125
126 static void unregisterPostfixInternal ( Operators::PostfixOperators type, const AlgorithmBaseInfo & entryInfo );
127
128public:
129 template < class FirstParam, class SecondParam >
131 unregisterBinaryInternal ( type, AlgorithmBaseInfo::operatorEntryInfo < FirstParam, SecondParam > ( ) );
132 }
133
134 template < class Return, class FirstParam, class SecondParam >
135 static void registerBinary ( Operators::BinaryOperators type, std::function < Return ( FirstParam, SecondParam ) > func ) {
136 registerBinaryInternal ( type, std::make_unique < BinaryOperator < Return, FirstParam, SecondParam > > ( func ) );
137 }
138
139 template < Operators::BinaryOperators Type, class FirstParam, class SecondParam >
140 static void registerBinary ( ) {
142 std::function < decltype ( std::declval < FirstParam > ( ) && std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a && b; };
144 } else if constexpr ( Type == Operators::BinaryOperators::LOGICAL_OR ) {
145 std::function < decltype ( std::declval < FirstParam > ( ) || std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a || b; };
147 } else if constexpr ( Type == Operators::BinaryOperators::BINARY_AND ) {
148 std::function < decltype ( std::declval < FirstParam > ( ) & std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a & b; };
150 } else if constexpr ( Type == Operators::BinaryOperators::BINARY_OR ) {
151 std::function < decltype ( std::declval < FirstParam > ( ) | std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a | b; };
153 } else if constexpr ( Type == Operators::BinaryOperators::BINARY_XOR ) {
154 std::function < decltype ( std::declval < FirstParam > ( ) ^ std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a ^ b; };
156 } else if constexpr ( Type == Operators::BinaryOperators::ADD ) {
157 std::function < decltype ( std::declval < FirstParam > ( ) + std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a + b; };
159 } else if constexpr ( Type == Operators::BinaryOperators::SUB ) {
160 std::function < decltype ( std::declval < FirstParam > ( ) - std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a - b; };
162 } else if constexpr ( Type == Operators::BinaryOperators::MUL ) {
163 std::function < decltype ( std::declval < FirstParam > ( ) * std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a * b; };
165 } else if constexpr ( Type == Operators::BinaryOperators::MOD ) {
166 std::function < decltype ( std::declval < FirstParam > ( ) % std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a % b; };
168 } else if constexpr ( Type == Operators::BinaryOperators::DIV ) {
169 std::function < decltype ( std::declval < FirstParam > ( ) / std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a / b; };
171 } else if constexpr ( Type == Operators::BinaryOperators::EQUALS ) {
172 std::function < decltype ( std::declval < FirstParam > ( ) == std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a == b; };
174 } else if constexpr ( Type == Operators::BinaryOperators::NOT_EQUALS ) {
175 std::function < decltype ( std::declval < FirstParam > ( ) != std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a != b; };
177 } else if constexpr ( Type == Operators::BinaryOperators::LESS ) {
178 std::function < decltype ( std::declval < FirstParam > ( ) < std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a < b; };
180 } else if constexpr ( Type == Operators::BinaryOperators::LESS_OR_EQUAL ) {
181 std::function < decltype ( std::declval < FirstParam > ( ) <= std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a <= b; };
183 } else if constexpr ( Type == Operators::BinaryOperators::MORE ) {
184 std::function < decltype ( std::declval < FirstParam > ( ) > std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a > b; };
186 } else if constexpr ( Type == Operators::BinaryOperators::MORE_OR_EQUAL ) {
187 std::function < decltype ( std::declval < FirstParam > ( ) >= std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) { return a >= b; };
189 } else if constexpr ( Type == Operators::BinaryOperators::ASSIGN ) {
190 std::function < decltype ( std::declval < FirstParam > ( ) = std::declval < SecondParam > ( ) ) ( FirstParam, SecondParam ) > callback = [ ] ( FirstParam a, SecondParam b ) -> decltype ( auto ) { return a = b; };
192 } else {
193 static_assert ( "Unhandled binary operator." );
194 }
195 }
196
197 static std::shared_ptr < abstraction::OperationAbstraction > getBinaryAbstraction ( Operators::BinaryOperators type, const ext::vector < std::string > & paramTypes, const ext::vector < abstraction::TypeQualifiers::TypeQualifierSet > & typeQualifiers, AlgorithmCategories::AlgorithmCategory category );
198
200
201
202 template < class Param >
204 unregisterPrefixInternal ( type, AlgorithmBaseInfo::operatorEntryInfo < Param > ( ) );
205 }
206
207 template < class Return, class Param >
208 static void registerPrefix ( Operators::PrefixOperators type, std::function < Return ( Param ) > func ) {
209 registerPrefixInternal ( type, std::make_unique < PrefixOperator < Return, Param > > ( func ) );
210 }
211
212 template < Operators::PrefixOperators Type, class Param >
213 static void registerPrefix ( ) {
214 if constexpr ( Type == Operators::PrefixOperators::PLUS ) {
215 std::function < decltype ( + std::declval < Param > ( ) ) ( Param ) > callback = [ ] ( Param a ) { return + a; };
217 } else if constexpr ( Type == Operators::PrefixOperators::MINUS ) {
218 std::function < decltype ( - std::declval < Param > ( ) ) ( Param ) > callback = [ ] ( Param a ) -> decltype ( auto ) { return - a; };
220 } else if constexpr ( Type == Operators::PrefixOperators::LOGICAL_NOT ) {
221 std::function < decltype ( ! std::declval < Param > ( ) ) ( Param ) > callback = [ ] ( Param a ) -> decltype ( auto ) { return ! a; };
223 } else if constexpr ( Type == Operators::PrefixOperators::BINARY_NEG ) {
224 std::function < decltype ( ~ std::declval < Param > ( ) ) ( Param ) > callback = [ ] ( Param a ) -> decltype ( auto ) { return ~ a; };
226 } else if constexpr ( Type == Operators::PrefixOperators::INCREMENT ) {
227 std::function < decltype ( ++ std::declval < Param > ( ) ) ( Param ) > callback = [ ] ( Param a ) -> decltype ( auto ) { return ++ a; };
229 } else if constexpr ( Type == Operators::PrefixOperators::DECREMENT ) {
230 std::function < decltype ( -- std::declval < Param > ( ) ) ( Param ) > callback = [ ] ( Param a ) -> decltype ( auto ) { return -- a; };
232 } else {
233 static_assert ( "Unhandled prefix operator." );
234 }
235 }
236
237 static std::shared_ptr < abstraction::OperationAbstraction > getPrefixAbstraction ( Operators::PrefixOperators type, const ext::vector < std::string > & paramTypes, const ext::vector < abstraction::TypeQualifiers::TypeQualifierSet > & typeQualifiers, AlgorithmCategories::AlgorithmCategory category );
238
240
241
242 template < class Param >
244 unregisterPostfixInternal ( type, AlgorithmBaseInfo::operatorEntryInfo < Param > ( ) );
245 }
246
247 template < class Return, class Param >
248 static void registerPostfix ( Operators::PostfixOperators type, std::function < Return ( Param ) > func ) {
249 registerPostfixInternal ( type, std::make_unique < PostfixOperator < Return, Param > > ( func ) );
250 }
251
252 template < Operators::PostfixOperators Type, class Param >
253 static void registerPostfix ( ) {
254 if constexpr ( Type == Operators::PostfixOperators::INCREMENT ) {
255 std::function < decltype ( std::declval < Param > ( ) ++ ) ( Param ) > callback = [ ] ( Param a ) { std::decay_t < Param > tmp = a; a ++; return tmp; };
257 } else if constexpr ( Type == Operators::PostfixOperators::DECREMENT ) {
258 std::function < decltype ( std::declval < Param > ( ) -- ) ( Param ) > callback = [ ] ( Param a ) { std::decay_t < Param > tmp = a; a --; return tmp; };
260 } else {
261 static_assert ( "Unhandled postfix operator." );
262 }
263 }
264
265 static std::shared_ptr < abstraction::OperationAbstraction > getPostfixAbstraction ( Operators::PostfixOperators type, const ext::vector < std::string > & paramTypes, const ext::vector < abstraction::TypeQualifiers::TypeQualifierSet > & typeQualifiers, AlgorithmCategories::AlgorithmCategory category );
266
268
269};
270
271} /* namespace abstraction */
272
276
277namespace abstraction {
278
279template < class Return, class FirstParam, class SecondParam >
280std::shared_ptr < abstraction::OperationAbstraction > OperatorRegistry::BinaryOperator < Return, FirstParam, SecondParam >::getAbstraction ( ) const {
281 return std::make_shared < abstraction::AlgorithmAbstraction < Return, FirstParam, SecondParam > > ( m_callback );
282}
283
284template < class Return, class Param >
285std::shared_ptr < abstraction::OperationAbstraction > OperatorRegistry::PrefixOperator < Return, Param >::getAbstraction ( ) const {
286 return std::make_shared < abstraction::AlgorithmAbstraction < Return, Param > > ( m_callback );
287}
288
289template < class Return, class Param >
290std::shared_ptr < abstraction::OperationAbstraction > OperatorRegistry::PostfixOperator < Return, Param >::getAbstraction ( ) const {
291 return std::make_shared < abstraction::AlgorithmAbstraction < Return, Param > > ( m_callback );
292}
293
294} /* namespace abstraction */
295
AlgorithmCategory
Definition: AlgorithmCategories.hpp:14
Definition: AlgorithmRegistryInfo.hpp:89
Definition: BaseRegistryEntry.hpp:12
Definition: OperatorRegistry.hpp:30
const AlgorithmFullInfo & getEntryInfo() const
Definition: OperatorRegistry.hpp:37
BinaryEntry(AlgorithmFullInfo entryInfo)
Definition: OperatorRegistry.hpp:34
Definition: OperatorRegistry.hpp:54
PostfixEntry(AlgorithmFullInfo entryInfo)
Definition: OperatorRegistry.hpp:58
const AlgorithmFullInfo & getEntryInfo() const
Definition: OperatorRegistry.hpp:61
Definition: OperatorRegistry.hpp:42
PrefixEntry(AlgorithmFullInfo entryInfo)
Definition: OperatorRegistry.hpp:46
const AlgorithmFullInfo & getEntryInfo() const
Definition: OperatorRegistry.hpp:49
Definition: OperatorRegistry.hpp:28
static std::shared_ptr< abstraction::OperationAbstraction > getPostfixAbstraction(Operators::PostfixOperators type, const ext::vector< std::string > &paramTypes, const ext::vector< abstraction::TypeQualifiers::TypeQualifierSet > &typeQualifiers, AlgorithmCategories::AlgorithmCategory category)
Definition: OperatorRegistry.cpp:154
static void registerBinary()
Definition: OperatorRegistry.hpp:140
static ext::list< ext::pair< Operators::PrefixOperators, AlgorithmFullInfo > > listPrefixOverloads()
Definition: OperatorRegistry.cpp:109
static void registerPostfix()
Definition: OperatorRegistry.hpp:253
static ext::list< ext::pair< Operators::BinaryOperators, AlgorithmFullInfo > > listBinaryOverloads()
Definition: OperatorRegistry.cpp:58
static void unregisterPostfix(Operators::PostfixOperators type)
Definition: OperatorRegistry.hpp:243
static void registerPrefix(Operators::PrefixOperators type, std::function< Return(Param) > func)
Definition: OperatorRegistry.hpp:208
static std::shared_ptr< abstraction::OperationAbstraction > getBinaryAbstraction(Operators::BinaryOperators type, const ext::vector< std::string > &paramTypes, const ext::vector< abstraction::TypeQualifiers::TypeQualifierSet > &typeQualifiers, AlgorithmCategories::AlgorithmCategory category)
Definition: OperatorRegistry.cpp:52
static void registerPostfix(Operators::PostfixOperators type, std::function< Return(Param) > func)
Definition: OperatorRegistry.hpp:248
static void unregisterPrefix(Operators::PrefixOperators type)
Definition: OperatorRegistry.hpp:203
static void registerPrefix()
Definition: OperatorRegistry.hpp:213
static void unregisterBinary(Operators::BinaryOperators type)
Definition: OperatorRegistry.hpp:130
static void registerBinary(Operators::BinaryOperators type, std::function< Return(FirstParam, SecondParam) > func)
Definition: OperatorRegistry.hpp:135
static std::shared_ptr< abstraction::OperationAbstraction > getPrefixAbstraction(Operators::PrefixOperators type, const ext::vector< std::string > &paramTypes, const ext::vector< abstraction::TypeQualifiers::TypeQualifierSet > &typeQualifiers, AlgorithmCategories::AlgorithmCategory category)
Definition: OperatorRegistry.cpp:103
static ext::list< ext::pair< Operators::PostfixOperators, AlgorithmFullInfo > > listPostfixOverloads()
Definition: OperatorRegistry.cpp:160
PostfixOperators
Definition: Operators.hpp:43
PrefixOperators
Definition: Operators.hpp:34
BinaryOperators
Definition: Operators.hpp:14
Class extending the list class from the standard library. Original reason is to allow printing of the...
Definition: list.hpp:44
Class extending the map class from the standard library. Original reason is to allow printing of the ...
Definition: map.hpp:48
Class extending the vector class from the standard library. Original reason is to allow printing of t...
Definition: vector.hpp:45
Definition: AlgorithmAbstraction.hpp:11
int callback(struct dl_phdr_info *info, size_t, void *data)
Definition: simpleStacktrace.cpp:25
Type
Definition: MeasurementTypes.hpp:20
Definition: FordFulkerson.hpp:16