Ariles
Loading...
Searching...
No Matches
common.h
Go to the documentation of this file.
1/**
2 @file
3 @author Alexander Sherikov
4
5 @copyright 2017-2020 Alexander Sherikov, Licensed under the Apache License, Version 2.0.
6 (see @ref LICENSE or http://www.apache.org/licenses/LICENSE-2.0)
7
8 @brief
9*/
10// cppcheck-suppress-file duplInheritedMember
11
12#pragma once
13
14#include <utility>
15#include <vector>
16#include <string_view>
17#include "../internal/helpers.h"
18
19namespace ariles2
20{
21 namespace visitor
22 {
24 {
25 public:
27
28 public:
29 explicit Parameters(const bool override_parameters = true)
30 {
31 override_parameters_ = override_parameters;
32 }
33 };
34
35
36 class Visitor
37 {
38 protected:
41 };
42
43
44 template <class t_Derived, class t_Parameters, class t_ReturnType = void>
45 class Base : public Visitor
46 {
47 public:
48 using ReturnType = t_ReturnType;
50
51 public:
52 virtual const t_Parameters &getDefaultParameters() const
53 {
54 const static t_Parameters parameters(false);
55 return parameters;
56 }
57
58 // cppcheck-suppress duplInheritedMember
59 template <class t_Ariles>
60 const t_Parameters &getParameters(const t_Ariles &ariles_class) const
61 {
62 return (ariles_class.arilesGetParameters(*static_cast<const t_Derived *>(this)));
63 }
64 };
65 } // namespace visitor
66
67
68#define ARILES2_BASE_METHODS(Namespace) \
69 using Namespace::Base::arilesVirtualVisit; \
70 using Namespace::Base::arilesGetParameters;
71
72#define ARILES2_METHODS(Namespace, VisitorQualifier, MethodQualifier) \
73 void arilesVirtualVisit( \
74 VisitorQualifier ariles2::Namespace::Visitor &visitor, \
75 const ariles2::Namespace::Visitor::Parameters &param) MethodQualifier override \
76 { \
77 CPPUT_TRACE_FUNCTION; \
78 this->arilesVisit(visitor, param); \
79 } \
80 using ariles2::Namespace::Base::arilesGetParameters;
81
82
83 namespace entry
84 {
85 template <class t_Visitor>
86 class Base
87 {
88 public:
89 virtual typename t_Visitor::ReturnType arilesVirtualVisit(
90 t_Visitor &,
91 const typename t_Visitor::Parameters &) = 0;
92
93 virtual const typename t_Visitor::Parameters &arilesGetParameters(const t_Visitor &visitor) const
94 {
96 return (visitor.getDefaultParameters());
97 }
98 };
99
100
101 template <class t_Visitor>
103 {
104 public:
105 virtual typename t_Visitor::ReturnType arilesVirtualVisit(
106 t_Visitor &,
107 const typename t_Visitor::Parameters &) const = 0;
108
109 virtual const typename t_Visitor::Parameters &arilesGetParameters(const t_Visitor &visitor) const
110 {
112 return (visitor.getDefaultParameters());
113 }
114 };
115 } // namespace entry
116
117 namespace traits
118 {
119 template <class t_Subtree>
120 using is_subtree = std::disjunction<
121 std::is_same<std::string, std::decay_t<t_Subtree>>, //
122 std::is_same<char *, std::decay_t<t_Subtree>>, //
123 std::is_same<const char *, std::decay_t<t_Subtree>>, //
124 std::is_same<std::string_view, std::decay_t<t_Subtree>>, //
125 std::is_same<std::vector<std::string>, std::decay_t<t_Subtree>>>;
126
127 template <class t_Subtree>
128 using is_subtree_t = std::enable_if_t<is_subtree<t_Subtree>::value>;
129
130 template <class t_Subtree>
131 using is_not_subtree_t = std::enable_if_t<not is_subtree<t_Subtree>::value>;
132
133
134 template <class t_Visitor>
135 using is_visitor_t = std::enable_if_t<std::is_base_of_v<ariles2::visitor::Visitor, t_Visitor>>;
136
137 template <class t_Visitor>
138 using is_not_visitor_t = std::enable_if_t<not std::is_base_of_v<ariles2::visitor::Visitor, t_Visitor>>;
139
140 template <class t_Ariles>
141 using is_ariles_t = std::enable_if_t<std::is_base_of_v<ariles2::Ariles, t_Ariles>>;
142
143 template <class t_Ariles>
144 using is_not_ariles_t = std::enable_if_t<not std::is_base_of_v<ariles2::Ariles, t_Ariles>>;
145 } // namespace traits
146} // namespace ariles2
147
148#ifndef ARILES2_DISABLE
149# ifndef ARILES2_ENABLED
150# define ARILES2_ENABLED
151# endif
152#endif
153
154#ifdef ARILES2_ENABLED
155
156namespace ariles2
157{
158 // -----
159 template <
160 class t_Ariles,
161 class t_Visitor,
162 class t_Subtree,
163 typename = traits::is_subtree_t<t_Subtree>,
164 typename = traits::is_visitor_t<t_Visitor>>
165 typename t_Visitor::ReturnType apply(
166 t_Visitor &visitor,
167 t_Ariles &ariles_class,
168 t_Subtree &&subtree,
169 const typename t_Visitor::Parameters &param)
170 {
172 return (visitor.visit(ariles_class, std::forward<t_Subtree>(subtree), param));
173 }
174
175
176 template <class t_Visitor, class t_Ariles, typename = traits::is_visitor_t<t_Visitor>>
177 typename t_Visitor::ReturnType apply(
178 t_Visitor &visitor,
179 t_Ariles &ariles_class,
180 const typename t_Visitor::Parameters &param)
181 {
183 return (visitor.visit(ariles_class, ariles_class.arilesDefaultID(), param));
184 }
185
186
187 template <
188 class t_Visitor,
189 class t_Ariles,
190 class t_Subtree,
191 typename = traits::is_subtree_t<t_Subtree>,
192 typename = traits::is_visitor_t<t_Visitor>>
193 typename t_Visitor::ReturnType apply(t_Visitor &visitor, t_Ariles &ariles_class, t_Subtree &&subtree)
194 {
196 return (visitor.visit(ariles_class, std::forward<t_Subtree>(subtree), visitor.getParameters(ariles_class)));
197 }
198
199
200 template <class t_Visitor, class t_Ariles, typename = traits::is_visitor_t<t_Visitor>>
201 typename t_Visitor::ReturnType apply(t_Visitor &visitor, t_Ariles &ariles_class)
202 {
204 return (ariles2::apply(visitor, ariles_class, ariles_class.arilesDefaultID()));
205 }
206
207
208 template <
209 class t_Visitor,
210 class t_Ariles,
211 typename = traits::is_visitor_t<t_Visitor>,
212 typename = traits::is_ariles_t<t_Ariles>>
213 typename t_Visitor::ReturnType apply(t_Ariles &ariles_class)
214 {
216 t_Visitor visitor;
217 return (ariles2::apply(visitor, ariles_class));
218 }
219 // -----
220
221
222
223 // -----
224 template <
225 class t_Visitor,
226 typename t_Arg,
227 typename... t_Args,
228 typename = traits::is_not_visitor_t<t_Arg>,
229 typename = traits::is_not_ariles_t<t_Arg>>
230 typename t_Visitor::ReturnType apply(t_Arg &&arg, t_Args &&...args)
231 {
233 t_Visitor visitor(std::forward<t_Arg>(arg));
234 return (ariles2::apply(visitor, std::forward<t_Args>(args)...));
235 }
236 // -----
237
238
239 // -----
240 template <
241 class t_Visitor,
242 class t_Left,
243 class t_Right,
244 typename = traits::is_visitor_t<t_Visitor>,
245 typename = traits::is_ariles_t<t_Left>,
246 typename = traits::is_not_subtree_t<t_Right>>
247 typename t_Visitor::ReturnType apply(t_Left &left, t_Right &right)
248 {
250 t_Visitor visitor;
251 return (visitor.visit(left, right, left.arilesDefaultID(), visitor.getParameters(left)));
252 }
253
254
255 template <
256 class t_Visitor,
257 class t_Left,
258 class t_Right,
259 typename = traits::is_not_subtree_t<t_Right>,
260 typename = traits::is_visitor_t<t_Visitor>>
261 typename t_Visitor::ReturnType apply(
262 t_Visitor &visitor,
263 t_Left &left,
264 t_Right &right,
265 const std::string &name,
266 const typename t_Visitor::Parameters &param)
267 {
269 return (visitor.visit(left, right, name, param));
270 }
271
272
273 template <
274 class t_Visitor,
275 class t_Left,
276 class t_Right,
277 typename = traits::is_visitor_t<t_Visitor>,
278 typename = traits::is_not_subtree_t<t_Right>,
279 typename = std::enable_if_t<not std::is_base_of_v<typename t_Visitor::Parameters, t_Right>>>
280 typename t_Visitor::ReturnType apply(t_Visitor &visitor, t_Left &left, t_Right &right)
281 {
283 return (visitor.visit(left, right, left.arilesDefaultID(), visitor.getParameters(left)));
284 }
285
286
287 template <
288 class t_Visitor,
289 class t_Left,
290 class t_Right,
291 typename = traits::is_not_subtree_t<t_Right>,
292 typename = traits::is_visitor_t<t_Visitor>>
293 typename t_Visitor::ReturnType apply(
294 t_Visitor &visitor,
295 t_Left &left,
296 t_Right &right,
297 const typename t_Visitor::Parameters &param)
298 {
300 return (ariles2::apply(visitor, left, right, left.arilesDefaultID(), param));
301 }
302 // -----
303} // namespace ariles2
304
305#else
306
307namespace ariles2
308{
309 template <class t_Visitor, class... t_Args>
310 void apply(t_Args &&.../*args*/)
311 {
312 }
313
314 template <class... t_Args>
315 void apply(t_Args &&.../*args*/)
316 {
317 }
318} // namespace ariles2
319
320#endif
virtual const t_Visitor::Parameters & arilesGetParameters(const t_Visitor &visitor) const
Definition common.h:93
virtual t_Visitor::ReturnType arilesVirtualVisit(t_Visitor &, const typename t_Visitor::Parameters &)=0
virtual const t_Visitor::Parameters & arilesGetParameters(const t_Visitor &visitor) const
Definition common.h:109
virtual t_Visitor::ReturnType arilesVirtualVisit(t_Visitor &, const typename t_Visitor::Parameters &) const =0
const t_Parameters & getParameters(const t_Ariles &ariles_class) const
Definition common.h:60
virtual const t_Parameters & getDefaultParameters() const
Definition common.h:52
t_ReturnType ReturnType
Definition common.h:48
Parameters(const bool override_parameters=true)
Definition common.h:29
std::enable_if_t< std::is_base_of_v< ariles2::visitor::Visitor, t_Visitor > > is_visitor_t
Definition common.h:135
std::enable_if_t< is_subtree< t_Subtree >::value > is_subtree_t
Definition common.h:128
std::enable_if_t< not std::is_base_of_v< ariles2::Ariles, t_Ariles > > is_not_ariles_t
Definition common.h:144
std::enable_if_t< std::is_base_of_v< ariles2::Ariles, t_Ariles > > is_ariles_t
Definition common.h:141
std::disjunction< std::is_same< std::string, std::decay_t< t_Subtree > >, std::is_same< char *, std::decay_t< t_Subtree > >, std::is_same< const char *, std::decay_t< t_Subtree > >, std::is_same< std::string_view, std::decay_t< t_Subtree > >, std::is_same< std::vector< std::string >, std::decay_t< t_Subtree > > > is_subtree
Definition common.h:125
std::enable_if_t< not std::is_base_of_v< ariles2::visitor::Visitor, t_Visitor > > is_not_visitor_t
Definition common.h:138
std::enable_if_t< not is_subtree< t_Subtree >::value > is_not_subtree_t
Definition common.h:131
t_Visitor::ReturnType apply(t_Visitor &visitor, t_Ariles &ariles_class, t_Subtree &&subtree, const typename t_Visitor::Parameters &param)
Definition common.h:165
#define CPPUT_TRACE_FUNCTION
Definition trace.h:126