Last active
April 29, 2019 13:31
-
-
Save xueliu/3a00ea64633a11b8dd3354eb658b32fd to your computer and use it in GitHub Desktop.
http://blog.coldflake.com/posts/C++-delegates-on-steroids/ https://github.com/marcmo/delegates 1. only c++11
2. only one delegate function
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#ifndef _DELEGATE_H_ | |
#define _DELEGATE_H_ | |
/** | |
* non specialized template declaration for delegate | |
*/ | |
template <typename T> | |
class delegate; | |
/** | |
* specialization for member functions | |
* | |
* \tparam T class-type of the object who's member function to call | |
* \tparam R return type of the function that gets captured | |
* \tparam params variadic template list for possible arguments | |
* of the captured function | |
*/ | |
template <typename T, typename R, typename... Params> | |
class delegate<R (T::*)(Params...)> | |
{ | |
public: | |
typedef R (T::*func_type)(Params...); | |
delegate(func_type func, T& callee) | |
: callee_(callee) | |
, func_(func) | |
{} | |
R operator()(Params... args) const | |
{ | |
return (callee_.*func_)(args...); | |
} | |
bool operator==(const delegate& other) const | |
{ | |
return (&callee_ == &other.callee_) && (func_ == other.func_); | |
} | |
bool operator!= (const delegate& other) const | |
{ | |
return !((*this) == other); | |
} | |
private: | |
T& callee_; | |
func_type func_; | |
}; | |
/** | |
* specialization for const member functions | |
*/ | |
template <typename T, typename R, typename... Params> | |
class delegate<R (T::*)(Params...) const> | |
{ | |
public: | |
typedef R (T::*func_type)(Params...) const; | |
delegate(func_type func, const T& callee) | |
: callee_(callee) | |
, func_(func) | |
{} | |
R operator()(Params... args) const | |
{ | |
return (callee_.*func_)(args...); | |
} | |
bool operator==(const delegate& other) const | |
{ | |
return (&callee_ == &other.callee_) && (func_ == other.func_); | |
} | |
bool operator!= (const delegate& other) const | |
{ | |
return !(*this == other); | |
} | |
private: | |
const T& callee_; | |
func_type func_; | |
}; | |
/** | |
* specialization for free functions | |
* | |
* \tparam R return type of the function that gets captured | |
* \tparam params variadic template list for possible arguments | |
* of the captured function | |
*/ | |
template <typename R, typename... Params> | |
class delegate<R (*)(Params...)> | |
{ | |
public: | |
typedef R (*func_type)(Params...); | |
delegate(func_type func) | |
: func_(func) | |
{} | |
R operator()(Params... args) const | |
{ | |
return (*func_)(args...); | |
} | |
bool operator==(const delegate& other) const | |
{ | |
return func_ == other.func_; | |
} | |
bool operator!= (const delegate& other) const | |
{ | |
return !((*this) == other); | |
} | |
private: | |
func_type func_; | |
}; | |
/** | |
* function to deduce template parameters from call-context | |
*/ | |
template <typename F, typename T> | |
delegate<F> make_delegate(F func, T& obj) | |
{ | |
return delegate<F>(func, obj); | |
} | |
template <typename T> | |
delegate<T> make_delegate(T func) | |
{ | |
return delegate<T>(func); | |
} | |
// a little backward compatilbility layer | |
#define DELEGATE make_delegate | |
#define DELEGATE_CONST make_delegate | |
#define DELEGATE_FREE make_delegate | |
#endif /* end of include guard */ |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <iostream> | |
#include "delegate.hpp" | |
class A | |
{ | |
public: | |
void deadSimple() | |
{ | |
printf("no params whatsoever\n"); | |
} | |
int foo(int x) | |
{ | |
return x*x; | |
} | |
int bar(int x, int y, char a) | |
{ | |
return a == 'a' ? x+y : x*y; | |
} | |
void crazy(int I, char wanna, float go, const char* crazy) | |
{ | |
printf("I=%d, wanna=%c, go=%f, crazy=%s\n", | |
I, wanna, go, crazy); | |
} | |
}; | |
int main() | |
{ | |
A a; | |
auto d = DELEGATE(&A::foo, a); | |
auto d2 = DELEGATE(&A::bar, a); | |
auto d3 = DELEGATE(&A::crazy, a); | |
auto d4 = DELEGATE(&A::deadSimple, a); | |
printf("d(42)=%d\n", d(42)); | |
printf("d2(42, 2, 'a')=%d\n", d2(42, 2, 'a')); | |
const char* s = "sheeeet!"; | |
d3(5, 'a', 4.5, s); | |
d4(); | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment