Chinaunix首页 | 论坛 | 博客
  • 博客访问: 2705273
  • 博文数量: 505
  • 博客积分: 1552
  • 博客等级: 上尉
  • 技术积分: 2514
  • 用 户 组: 普通用户
  • 注册时间: 2007-09-23 18:24
文章分类

全部博文(505)

文章存档

2019年(12)

2018年(15)

2017年(1)

2016年(17)

2015年(14)

2014年(93)

2013年(233)

2012年(108)

2011年(1)

2009年(11)

分类: C/C++

2013-07-28 21:25:00

众所周知,C++的类成员函数不能像普通函数那样用于回调,因为每个成员函数都需要有一个对象实例去调用它。

        通常情况下,要实现成员函数作为回调函数,一种常用的方法就是把该成员函数设计为静态成员函数,但这样做有一个缺点,就是会破坏类的结构性,因为静态成员 函数只能访问该类的静态成员变量和静态成员函数,不能访问非静态的,要解决这个问题,需要把对象实例的指针或引用做为参数传给它。

        在一次偶然的机会下,看到了一种方法可以简单的实现回调非静态成员函数,其原理就是把要调用该成员函数的对象实例赋值给一个变量,然后通过该变量来调用成 员函数。把逻辑整理了一下,然后写了一个简单的回调代理类,通过这个类,可以简单的实现非静态函数的回调。


CallbackProxy.h

点击(此处)折叠或打开

  1. #ifndef __CALLBACK_PROXY_H__ 
  2. #define __CALLBACK_PROXY_H__
  3.   
  4. //Tobject:调用对象的类型,Tparam回调函数参数的类型
  5. template<typename Tobject, typename Tparam>
  6. class CCallbackProxy
  7. {
  8.     typedef void (Tobject::*CbFun)(Tparam*);
  9.   
  10. public:
  11.     void Set(Tobject *pInstance, CbFun pFun);
  12.     bool Exec(Tparam* pParam);
  13.   
  14. private:
  15.     CbFun pCbFun; //回调函数指针
  16.     Tobject* m_pInstance; //调用对象
  17. };
  18.   
  19. //设置调用对象及其回调函数
  20. template<typename Tobject, typename Tparam>
  21. void CCallbackProxy<Tobject, Tparam>::Set(Tobject *pInstance , CbFun pFun)
  22. {
  23.     m_pInstance = pInstance;
  24.     pCbFun = pFun;
  25. };
  26.   
  27. //调用回调函数
  28. template<typename Tobject, typename Tparam>
  29. bool CCallbackProxy<Tobject, Tparam>::Exec(Tparam* pParam)
  30. {
  31.     (m_pInstance->*pCbFun)(pParam);
  32.     return true;
  33. }
  34.   
  35. #endif

下面演示下如何使用该类
test.cpp

点击(此处)折叠或打开

  1. #include "CallbackProxy.h"
  2.   
  3. class CTest
  4. {
  5. public:
  6.     CTest(int nNum);
  7.     void CbPrintSum(int *pnAddNum){printf("The Sum is %d\n", m_nSum+*pnAddNum);};
  8.   
  9. private:
  10.     int m_nSum;
  11. };
  12.   
  13. int main(int argc, char* argv[])
  14. {
  15.     CCallbackProxy<CTest, int> CbProxy;
  16.   
  17.     CTest TestInstance(20);
  18.   
  19.     CbProxy.Set(&TestInstance, &CTest::CbPrintSum);
  20.   
  21.     int nNum = 1000;
  22.     CbProxy.Exec(&nNum);
  23.   
  24.     return 0;
  25. }
  26.   
  27. CTest::CTest(int nNum):
  28. m_nSum(nNum)
  29. {
  30.   
  31. }


阅读(2650) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~