#ifndef THREE_H #define THREE_H namespace three { struct Strategy1 { void f() { std::cout << "strategy 1" << std::endl; } }; struct Strategy2 { void g() { std::cout << "strategy 2" << std::endl; } }; template void adapt( T* t) { t->f(); } template <> void adapt( Strategy2* t) { t->g(); } struct IStrategy { template IStrategy(T* x) : x_(x), fun_(vTable_::f) {} void f() const { fun_(x_); } private: typedef void (*FUN)(void*); template struct vTable_ { static void f(void* x) { adapt(static_cast(x)); } }; private: FUN fun_; void* x_; }; struct Context { Context(const IStrategy& strategy) : strategy_(strategy) {} void f() const { strategy_.f(); } private: const IStrategy& strategy_; }; void test() { Strategy1 s1; Strategy2 s2; IStrategy i(&s1); Context c(i); c.f(); i = &s2; c.f(); } } #endif