CppCMS
function.h
1 //
2 // Copyright (C) 2009-2012 Artyom Beilis (Tonkikh)
3 //
4 // Distributed under the Boost Software License, Version 1.0. (See
5 // accompanying file LICENSE_1_0.txt or copy at
6 // http://www.boost.org/LICENSE_1_0.txt)
7 //
8 #ifndef BOOSTER_FUNCTION_H
9 #define BOOSTER_FUNCTION_H
10 
11 #include <booster/backtrace.h>
12 #include <booster/clone_ptr.h>
13 
14 namespace booster {
15  template<typename Type>
16  class function;
17 
23  public:
25  booster::runtime_error("bad_function_call")
26  {
27  }
28  };
29 
30 
31  #ifdef BOOSTER_DOXYGEN_DOCS
32  template<typename Result,typename ...Params>
50  class function<Result(Params...)>
51  {
52  public:
56  typedef Result result_type;
60  function();
65  template<typename F>
66  function(F func);
67 
71  function(function const &other);
72 
77  template<typename F>
78  function const &operator=(F func);
79 
83  function const &operator=(function const &other);
84 
88  result_type operator()(Params... params) const;
92  bool empty() const;
96  operator bool() const;
97 
101  void swap(function &other);
102  };
103 
104  #else
105 
106  #define BOOSTER_FUNCTION \
107  template<typename Result BOOSTER_TEMPLATE_PARAMS > \
108  class function<Result(BOOSTER_TEMPLATE_TYPE_PARAMS)> \
109  { \
110  public: \
111  typedef Result result_type; \
112  struct callable { \
113  virtual Result call(BOOSTER_TYPE_PARAMS) =0; \
114  virtual callable *clone() const = 0; \
115  virtual ~callable(){} \
116  }; \
117  \
118  template<typename R,typename F> \
119  struct callable_impl : public callable { \
120  F func; \
121  callable_impl(F f) : func(f){} \
122  virtual R call(BOOSTER_TYPE_PARAMS) \
123  { return func(BOOSTER_CALL_PARAMS); } \
124  virtual callable *clone() const \
125  { return new callable_impl<R,F>(func); } \
126  }; \
127  template<typename F> \
128  struct callable_impl<void,F> : public callable { \
129  F func; \
130  callable_impl(F f) : func(f){} \
131  virtual void call(BOOSTER_TYPE_PARAMS) \
132  { func(BOOSTER_CALL_PARAMS); } \
133  virtual callable *clone() const \
134  { return new callable_impl<void,F>(func); } \
135  }; \
136  function(){} \
137  template<typename F> \
138  function(F func) : call_ptr(new callable_impl<Result,F>(func)) \
139  {} \
140  function(function const &other) : call_ptr(other.call_ptr) {} \
141  template<typename F> \
142  function const &operator=(F func) \
143  { \
144  call_ptr.reset(new callable_impl<Result,F>(func)); \
145  return *this; \
146  } \
147  function const &operator=(function const &other) \
148  { \
149  if(this != &other) { call_ptr=other.call_ptr; } \
150  return *this; \
151  } \
152  Result operator()(BOOSTER_TYPE_PARAMS) const \
153  { \
154  if(!call_ptr.get()) throw bad_function_call(); \
155  return call_ptr->call(BOOSTER_CALL_PARAMS); \
156  } \
157  bool empty() const { return call_ptr.get()==0; } \
158  operator bool() const { return !empty(); } \
159  void swap(function &other) { call_ptr.swap(other.call_ptr); } \
160  private: \
161  clone_ptr<callable> call_ptr; \
162  }; \
163 
164  #define BOOSTER_TEMPLATE_PARAMS
165  #define BOOSTER_TEMPLATE_TYPE_PARAMS
166  #define BOOSTER_TYPE_PARAMS
167  #define BOOSTER_CALL_PARAMS
168  BOOSTER_FUNCTION
169  #undef BOOSTER_TEMPLATE_PARAMS
170  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
171  #undef BOOSTER_TYPE_PARAMS
172  #undef BOOSTER_CALL_PARAMS
173 
174  #define BOOSTER_TEMPLATE_PARAMS ,typename P1
175  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1
176  #define BOOSTER_TYPE_PARAMS P1 a1
177  #define BOOSTER_CALL_PARAMS a1
178  BOOSTER_FUNCTION
179  #undef BOOSTER_TEMPLATE_PARAMS
180  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
181  #undef BOOSTER_TYPE_PARAMS
182  #undef BOOSTER_CALL_PARAMS
183 
184  #define BOOSTER_TEMPLATE_PARAMS ,typename P1,typename P2
185  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1, P2
186  #define BOOSTER_TYPE_PARAMS P1 a1,P2 a2
187  #define BOOSTER_CALL_PARAMS a1,a2
188  BOOSTER_FUNCTION
189  #undef BOOSTER_TEMPLATE_PARAMS
190  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
191  #undef BOOSTER_TYPE_PARAMS
192  #undef BOOSTER_CALL_PARAMS
193 
194  #define BOOSTER_TEMPLATE_PARAMS ,typename P1,typename P2,typename P3
195  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1, P2, P3
196  #define BOOSTER_TYPE_PARAMS P1 a1,P2 a2,P3 a3
197  #define BOOSTER_CALL_PARAMS a1,a2,a3
198  BOOSTER_FUNCTION
199  #undef BOOSTER_TEMPLATE_PARAMS
200  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
201  #undef BOOSTER_TYPE_PARAMS
202  #undef BOOSTER_CALL_PARAMS
203 
204  #define BOOSTER_TEMPLATE_PARAMS ,typename P1,typename P2,typename P3,typename P4
205  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1, P2, P3, P4
206  #define BOOSTER_TYPE_PARAMS P1 a1,P2 a2,P3 a3,P4 a4
207  #define BOOSTER_CALL_PARAMS a1,a2,a3,a4
208  BOOSTER_FUNCTION
209  #undef BOOSTER_TEMPLATE_PARAMS
210  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
211  #undef BOOSTER_TYPE_PARAMS
212  #undef BOOSTER_CALL_PARAMS
213 
214  #define BOOSTER_TEMPLATE_PARAMS ,typename P1,typename P2,typename P3,typename P4,typename P5
215  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1, P2, P3, P4, P5
216  #define BOOSTER_TYPE_PARAMS P1 a1,P2 a2,P3 a3,P4 a4,P5 a5
217  #define BOOSTER_CALL_PARAMS a1,a2,a3,a4,a5
218  BOOSTER_FUNCTION
219  #undef BOOSTER_TEMPLATE_PARAMS
220  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
221  #undef BOOSTER_TYPE_PARAMS
222  #undef BOOSTER_CALL_PARAMS
223 
224  #define BOOSTER_TEMPLATE_PARAMS ,typename P1,typename P2,typename P3,typename P4,typename P5,typename P6
225  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1, P2, P3, P4, P5, P6
226  #define BOOSTER_TYPE_PARAMS P1 a1,P2 a2,P3 a3,P4 a4,P5 a5,P6 a6
227  #define BOOSTER_CALL_PARAMS a1,a2,a3,a4,a5,a6
228  BOOSTER_FUNCTION
229  #undef BOOSTER_TEMPLATE_PARAMS
230  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
231  #undef BOOSTER_TYPE_PARAMS
232  #undef BOOSTER_CALL_PARAMS
233 
234  #define BOOSTER_TEMPLATE_PARAMS ,typename P1,typename P2,typename P3,typename P4,typename P5,typename P6,typename P7
235  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1, P2, P3, P4, P5, P6, P7
236  #define BOOSTER_TYPE_PARAMS P1 a1,P2 a2,P3 a3,P4 a4,P5 a5,P6 a6,P7 a7
237  #define BOOSTER_CALL_PARAMS a1,a2,a3,a4,a5,a6,a7
238  BOOSTER_FUNCTION
239  #undef BOOSTER_TEMPLATE_PARAMS
240  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
241  #undef BOOSTER_TYPE_PARAMS
242  #undef BOOSTER_CALL_PARAMS
243 
244  #define BOOSTER_TEMPLATE_PARAMS ,typename P1,typename P2,typename P3,typename P4,typename P5,typename P6,typename P7,typename P8
245  #define BOOSTER_TEMPLATE_TYPE_PARAMS P1, P2, P3, P4, P5, P6, P7, P8
246  #define BOOSTER_TYPE_PARAMS P1 a1,P2 a2,P3 a3,P4 a4,P5 a5,P6 a6,P7 a7,P8 a8
247  #define BOOSTER_CALL_PARAMS a1,a2,a3,a4,a5,a6,a7,a8
248  BOOSTER_FUNCTION
249  #undef BOOSTER_TEMPLATE_PARAMS
250  #undef BOOSTER_TEMPLATE_TYPE_PARAMS
251  #undef BOOSTER_TYPE_PARAMS
252  #undef BOOSTER_CALL_PARAMS
253 
254  #undef BOOSTER_FUNCTION
255 
256  #endif // DOC
257 
258 } // booster
259 
260 
261 #endif
Same as std::runtime_error but records stack trace.
Definition: backtrace.h:158
Result result_type
Definition: function.h:56
Definition: function.h:16
This exception is thrown in case of an attempt to call to unassigned booster::function.
Definition: function.h:22
Booster library namespace. The library that implements Boost Like API in ABI backward compatible way...
Definition: application.h:23