Manak  2.0.0
template_utils.hpp
Go to the documentation of this file.
1 
7 #ifndef MANAK_UTIL_TEMPLATE_UTILS_HPP_INCLUDED
8 #define MANAK_UTIL_TEMPLATE_UTILS_HPP_INCLUDED
9 
10 namespace manak
11 {
12 namespace utils
13 {
14 namespace helper
15 {
16 
17 template<int>
19 
20 }; // namespace helper
21 }; // namespace utils
22 }; // namespace manak
23 
24 namespace std
25 {
27  template<int N>
28  struct is_placeholder<manak::utils::helper::template_placeholder<N>>
29  : integral_constant<int, N> // the one is important
30  {};
31 }
32 
33 namespace manak
34 {
35 namespace utils
36 {
37 namespace helper
38 {
39 
40 template<int... Args>
41 struct Hold
42 {
43 };
44 
45 template<int N, int... Args>
47 {
48  return Hold<Args..., N>();
49 }
50 
51 template<int N>
52 struct SGenerate
53 {
54  typedef decltype(Combine(typename SGenerate<N - 1>::type(), Hold<N>())) type;
55 };
56 
57 template<>
58 struct SGenerate<1>
59 {
60  typedef Hold<1> type;
61 };
62 
63 template<typename RType, typename... Args>
64 RType Caller_3(std::function<RType(Args...)> fun, Args... args)
65 {
66  return fun(args...);
67 }
68 
69 template<typename RType, typename Fun, typename P, int... S>
70 RType Caller_2(Fun fun, P params, Hold<S...>)
71 {
72  return fun(std::get<S - 1>(params)...);
73 }
74 
75 template<int>
76 struct template_placeholder
77 {
78 
79 };
80 
81 template<typename RType, typename F, typename O, int... S>
82 RType BindToObject2(F fun, const O* o, Hold<S...>)
83 {
84  return std::bind(fun, o, template_placeholder<S>()...);
85 }
86 
87 template<typename RType, typename F, typename O, int... S>
88 RType BindToObject2(F fun, O* o, Hold<S...>)
89 {
90  return std::bind(fun, o, template_placeholder<S>()...);
91 }
92 
93 template<typename RType, typename F, typename O>
94 RType BindToObject2(F fun, const O* o)
95 {
96  return std::bind(fun, o);
97 }
98 
99 template<typename RType, typename F, typename O>
100 RType BindToObject2(F fun, O* o)
101 {
102  return std::bind(fun, o);
103 }
104 
105 }; // namespace helpers
106 
107 template<typename RType, typename P, typename... Args>
108 RType Caller(std::function<RType(Args...)> fun, P params)
109 {
110  return helper::Caller_2<RType>(fun, params, typename helper::SGenerate<sizeof...(Args)>::type());
111 }
112 
113 //template<typename RType, typename... Args>
114 //RType Caller(RType (fun)(Args...), std::tuple<Args...> params)
115 //{
116 // return helper::Caller_2<RType>(fun, params, typename helper::SGenerate<sizeof...(Args)>::type());
117 //}
118 
119 template<typename RType, typename P, typename... Args>
120 RType Caller(RType (*fun)(Args...), P params)
121 {
122  return helper::Caller_2<RType>(fun, params, typename helper::SGenerate<sizeof...(Args)>::type());
123 }
124 
125 
126 template<typename RType, typename C, typename... Args>
127 std::function<RType(Args...)> BindToObject(RType (C::*fun)(Args...), C* c)
128 {
129  return helper::BindToObject2<std::function<RType(Args...)>>(fun, c, typename helper::SGenerate<sizeof...(Args)>::type());
130 }
131 
132 template<typename RType, typename C, typename... Args>
133 std::function<RType(Args...)> BindToObject(RType (C::*fun)(Args...) const, const C* c)
134 {
135  return helper::BindToObject2<std::function<RType(Args...)>>(fun, c, typename helper::SGenerate<sizeof...(Args)>::type());
136 }
137 
138 template<typename RType, typename C, typename... Args>
139 std::function<RType(Args...)> BindToObject(RType (C::*fun)(Args...) const, C* c)
140 {
141  return helper::BindToObject2<std::function<RType(Args...)>>(fun, c, typename helper::SGenerate<sizeof...(Args)>::type());
142 }
143 
144 template<typename RType, typename C, typename... Args>
145 std::function<RType(Args...)> BindToObject(RType (C::*fun)(), C* c)
146 {
147  return helper::BindToObject2<std::function<RType(Args...)>>(fun, c);
148 }
149 
150 template<typename RType, typename C, typename... Args>
151 std::function<RType(Args...)> BindToObject(RType (C::*fun)() const, const C* c)
152 {
153  return helper::BindToObject2<std::function<RType(Args...)>>(fun, c);
154 }
155 
156 template<typename RType, typename C, typename... Args>
157 std::function<RType(Args...)> BindToObject(RType (C::*fun)() const, C* c)
158 {
159  return helper::BindToObject2<std::function<RType(Args...)>>(fun, c);
160 }
161 
162 template<typename U, void (U::*)()> struct manak_group_test{};
163 
164 }; // namespace utils
165 }; // namespace manak
166 
167 
168 #endif // MANAK_UTIL_TEMPLATE_UTILS_HPP_INCLUDED
RType Caller(std::function< RType(Args...)> fun, P params)
RType Caller_3(std::function< RType(Args...)> fun, Args...args)
RType BindToObject2(F fun, const O *o, Hold< S...>)
Hold< Args..., N > Combine(Hold< Args...>, Hold< N >)
std::function< RType(Args...)> BindToObject(RType(C::*fun)(Args...), C *c)
RType Caller_2(Fun fun, P params, Hold< S...>)
decltype(Combine(typename SGenerate< N-1 >::type(), Hold< N >())) typedef type