AIToolbox
A library that offers tools for AI problem solving.
FunctionMatching.hpp
Go to the documentation of this file.
1 #ifndef AI_TOOLBOX_IMPL_FUNCTION_MATCHIN_HEADER_FILE
2 #define AI_TOOLBOX_IMPL_FUNCTION_MATCHIN_HEADER_FILE
3 
4 #include <tuple>
5 
7 
8 namespace AIToolbox::Impl {
38  template <typename T>
40 
41  template <typename R, typename... Args>
42  struct GetFunctionArguments<R(*)(Args...)> {
43  using args = std::tuple<Args...>;
44  using rettype = R;
45  };
46 
47  template <typename R, typename C, typename... Args>
48  struct GetFunctionArguments<R(C::*)(Args...)> {
49  using args = std::tuple<Args...>;
50  using rettype = R;
51  };
52 
53  template <typename R, typename C, typename... Args>
54  struct GetFunctionArguments<R(C::*)(Args...) const> : GetFunctionArguments<R(C::*)(Args...)> {};
55 
59  template <size_t... IDs> struct IdPack {};
60 
75  template <size_t N, typename T, typename U, size_t... IDs>
76  struct Matcher {
77  static constexpr bool match = false;
78  using type = IdPack<IDs...>;
79  };
80 
81  template <size_t N, typename... B, size_t... IDs>
82  struct Matcher<N, std::tuple<>, std::tuple<B...>, IDs...> {
83  static constexpr bool match = true;
84  using type = IdPack<IDs...>;
85  };
86 
87  template <size_t N, typename F, typename... A, typename... B, size_t... IDs>
88  struct Matcher<N, std::tuple<F, A...>, std::tuple<F, B...>, IDs...> {
89  using M = Matcher<N+1, std::tuple<A...>, std::tuple<B...>, IDs..., N>;
90  static constexpr bool match = M::match;
91  using type = typename M::type;
92  };
93 
94  template <size_t N, typename FA, typename... A, typename FB, typename... B, size_t... IDs>
95  struct Matcher<N, std::tuple<FA, A...>, std::tuple<FB, B...>, IDs...> {
96  using M = std::conditional_t<
97  std::is_constructible_v<FA, FB> &&
98  std::is_same_v<std::remove_cvref_t<FA>, std::remove_cvref_t<FB>>,
99  Matcher<N+1, std::tuple<A...>, std::tuple<B...>, IDs..., N>,
100  Matcher<N+1, std::tuple<FA, A...>, std::tuple<B...>, IDs...>
101  >;
102  static constexpr bool match = M::match;
103  using type = typename M::type;
104  };
105 
116  template <typename T, typename F>
118  static constexpr bool value = false;
119  };
120 
121  template <typename R, typename... Args, typename R2, typename... Args2>
122  struct is_compatible_f<R(Args...), R2(Args2...)> {
123  static constexpr bool value = std::is_same<R, R2>::value &&
124  Matcher<0, std::tuple<Args...>, std::tuple<Args2...>>::match;
125  };
126 
127  template <typename R, typename C, typename... Args, typename R2, typename... Args2>
128  struct is_compatible_f<R(C::*)(Args...), R2(Args2...)> : is_compatible_f<R(Args...), R2(Args2...)> {};
129 
130  template <typename R, typename C, typename... Args, typename R2, typename... Args2>
131  struct is_compatible_f<R(C::*)(Args...) const, R2(Args2...)> : is_compatible_f<R(C::*)(Args...), R2(Args2...)> {};
132 
141  template <typename F, typename... Args, size_t... IDs>
142  void caller(F f, std::tuple<Args...> && args, IdPack<IDs...>) {
143  f(std::forward<std::tuple_element_t<IDs, std::tuple<Args...>>>(std::get<IDs>(args))...);
144  }
145 
146  template <typename C, typename F, typename... Args, size_t... IDs>
147  void caller(C & c, F f, std::tuple<Args...> && args, IdPack<IDs...>) {
148  (c.*f)(std::forward<std::tuple_element_t<IDs, std::tuple<Args...>>>(std::get<IDs>(args))...);
149  }
150 
162  template <typename F, typename... Args>
163  void callFunction(F f, Args&& ...args) {
164  using FArgs = typename GetFunctionArguments<F>::args;
165  using IdList = typename Matcher<0, FArgs, std::tuple<Args...>>::type;
166 
167  caller(f, std::forward_as_tuple(args...), IdList());
168  }
169 
182  template <typename C, typename F, typename... Args>
183  void callFunction(C & c, F f, Args&& ...args) {
184  using FArgs = typename GetFunctionArguments<F>::args;
185  using IdList = typename Matcher<0, FArgs, std::tuple<Args...>>::type;
186  static_assert(Matcher<0, FArgs, std::tuple<Args...>>::match);
187 
188  caller(c, f, std::forward_as_tuple(args...), IdList());
189  }
190 
192 }
193 
194 #endif
AIToolbox::Impl::Matcher::match
static constexpr bool match
Definition: FunctionMatching.hpp:77
AIToolbox::Impl::is_compatible_f
This struct reports whether a given function is compatible with a given signature.
Definition: FunctionMatching.hpp:117
AIToolbox::Impl::GetFunctionArguments
This struct helps decompose a function into return value and arguments.
Definition: FunctionMatching.hpp:39
AIToolbox::Impl::Matcher
This struct allows to match between two tuples types.
Definition: FunctionMatching.hpp:76
AIToolbox::Impl::Matcher< N, std::tuple< FA, A... >, std::tuple< FB, B... >, IDs... >::M
std::conditional_t< std::is_constructible_v< FA, FB > &&std::is_same_v< std::remove_cvref_t< FA >, std::remove_cvref_t< FB > >, Matcher< N+1, std::tuple< A... >, std::tuple< B... >, IDs..., N >, Matcher< N+1, std::tuple< FA, A... >, std::tuple< B... >, IDs... > > M
Definition: FunctionMatching.hpp:101
AIToolbox::Impl::caller
void caller(F f, std::tuple< Args... > &&args, IdPack< IDs... >)
This function calls the input function with the subset of correct parameters from the input tuple.
Definition: FunctionMatching.hpp:142
AIToolbox::Impl::IdPack
This class is simply a template container for ids.
Definition: FunctionMatching.hpp:59
TypeTraits.hpp
AIToolbox::Factored::match
bool match(const PartialFactors &lhs, const PartialFactors &rhs)
This function returns whether the common factors in the inputs match in value.
AIToolbox::Impl::is_compatible_f::value
static constexpr bool value
Definition: FunctionMatching.hpp:118
AIToolbox::Impl
Definition: FunctionMatching.hpp:8
AIToolbox::Impl::GetFunctionArguments< R(C::*)(Args...)>::rettype
R rettype
Definition: FunctionMatching.hpp:50
AIToolbox::Impl::Matcher< N, std::tuple< FA, A... >, std::tuple< FB, B... >, IDs... >::type
typename M::type type
Definition: FunctionMatching.hpp:103
AIToolbox::Impl::GetFunctionArguments< R(C::*)(Args...)>::args
std::tuple< Args... > args
Definition: FunctionMatching.hpp:49
AIToolbox::Impl::callFunction
void callFunction(F f, Args &&...args)
This function calls the input function with the specified arguments.
Definition: FunctionMatching.hpp:163
AIToolbox::Impl::GetFunctionArguments< R(*)(Args...)>::rettype
R rettype
Definition: FunctionMatching.hpp:44
AIToolbox::Impl::Matcher< N, std::tuple< F, A... >, std::tuple< F, B... >, IDs... >::type
typename M::type type
Definition: FunctionMatching.hpp:91
AIToolbox::Impl::GetFunctionArguments< R(*)(Args...)>::args
std::tuple< Args... > args
Definition: FunctionMatching.hpp:43