从cocos2dx中寻找函数指针传递的方法
目的
看到群里有个朋友搞了好几天函数指针传递,没搞好。所以写一篇文章,旨在从cocos2dx中帮朋友们找到如何传递指针。
旧版本的函数指针传递
全局函数函数指针调用
一般在C++11之前,我们一般是这样定义一个函数指针类型。
- typede void(*pFunc)(int,...);
什么意思呢?
- typedef void/*return type of function*/
- (*pFunc/*the pointer of function*/)
- (int,.../*the types of function parameters*/);
- typedef void/*函数返回类型*/(*pFunc/*函数指针*/)(int,.../*函数参数类型*/);
OK,那么好了,该如何调用呢?
一般来说是像下面这样的。
- typedef void(*pFunc)();
- void fA(){ };
- void fB(pFunc pf){ (*pf)(/*里面加函数参数*/) };
- void fC(){ fB(&fA);};
即为在fC中调用fB,fB的参数为fA指针。
成员函数函数指针的调用
那么成员函数如何调用呢?
只需要加一个类名修饰符即可。
示例如下:
- class C;
- typedef void(C::*pFunc)();
- void C::fA(){};
- void C::fB(pFunc pf){ (this->*pf)()};
- void C::fC(){this->fB(&C::fA);};
其实,有心的朋友应该会注意到cocos2dx 版本中的各种selector即为宏定义的函数指针的引用,定义如下:
- typedef void (Ref::*SEL_CallFunc)();
- typedef void (Ref::*SEL_CallFuncN)(Node*);
- typedef void (Ref::*SEL_CallFuncND)(Node*, void*);
- typedef void (Ref::*SEL_CallFuncO)(Ref*);
- typedef void (Ref::*SEL_MenuHandler)(Ref*);
- typedef void (Ref::*SEL_SCHEDULE)(float);
- #define callfunc_selector(_SELECTOR) static_cast<cocos2d::SEL_CallFunc>(&_SELECTOR)
- #define callfuncN_selector(_SELECTOR) static_cast<cocos2d::SEL_CallFuncN>(&_SELECTOR)
- #define callfuncND_selector(_SELECTOR) static_cast<cocos2d::SEL_CallFuncND>(&_SELECTOR)
- #define callfuncO_selector(_SELECTOR) static_cast<cocos2d::SEL_CallFuncO>(&_SELECTOR)
- #define menu_selector(_SELECTOR) static_cast<cocos2d::SEL_MenuHandler>(&_SELECTOR)
- #define schedule_selector(_SELECTOR) static_cast<cocos2d::SEL_SCHEDULE>(&_SELECTOR)
所以不懂函数指针的朋友完全可以模仿它。 相信你很快就能上手。
C++11 中std::function的应用
cocos2dx 里面std::function定义的各种回调的解析
假设我们不知道std::function如何使用,那么只有浏览cocos2dx3.X里面的源码,我们会发现有大量的callBack 是用std::function定义的。
我们在此,首先用cocos2dx里面的网络http请求的返回函数举例。
HttpRequest 的回调定义为
inline void setResponseCallback(const ccHttpRequestCallback& callback)
{
_pCallback = callback;
}
追踪ccHttpRequestCallback,可以发现ccHttpRequestCallback即为std::function定义的:
typedef std::function<void(HttpClient* client, HttpResponse* response)> ccHttpRequestCallback;
使用过的同学应该知道怎么调用的,
一般都是 setResponseCallback(CC_CALLBACK_2(ClassName::jsonRequestCompleted,this));
CC_CALLBACK是什么东东,其实就是std::bind的引用宏定义。我们查看定义如下:
- #define CC_CALLBACK_0(__selector__,__target__, ...) std::bind(&__selector__,__target__, ##__VA_ARGS__)
- #define CC_CALLBACK_1(__selector__,__target__, ...) std::bind(&__selector__,__target__, std::placeholders::_1, ##__VA_ARGS__)
- #define CC_CALLBACK_2(__selector__,__target__, ...) std::bind(&__selector__,__target__, std::placeholders::_1, std::placeholders::_2, ##__VA_ARGS__)
- #define CC_CALLBACK_3(__selector__,__target__, ...) std::bind(&__selector__,__target__, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, ##__VA_ARGS__)
很明显,CC_CALLBACK_2就是 std::bind里面传参数,第一个是引用参数表示函数,第二个是目标,第三个,第四个是占位符,后面是不定参数。
所以可以等价代换为std::bind,那么我们上面的回调可以变成
setResponseCallback(std::bind(&ClassName::jsonRequestCompleted,this,std::placeholders::_1,std::placeholders::_2));
自定义std::function的应用
通过以上分析,相信大家已经掌握了如何通过std::function传递函数,以及std::bind去调用。不过为了照顾一些基础薄弱的朋友,我还是给出一个简单的例子。
- class C;
- void C::fA(){}
- void C::fB(const std::function<void()> &func)
- {
- if (func)
- {
- func();
- }
- }
- void C::fC()
- {
- fB(std::bind(&c::fA,this));
- }
关于非成员函数使用std::function
非成员函数使用std::function和上面的函数指针实际上是一致的,鉴于它比较容易,就不在此赘述了,还不会的朋友可以试一下。
申明:
本文原创,转载请注明出处。http://blog.csdn.net/q229827701/article/details/41479753
从cocos2dx中寻找函数指针传递的方法的更多相关文章
- 1、C语言中的函数指针
一 通常的函数调用 void MyFun(int x); //此处的申明也可写成:void MyFun( int ); int main(int argc, char* argv[]) { MyFun ...
- Keil C51 中的函数指针和再入函数
函数指针是C语言中几个难点之一.由于8051的C编译器的独特要求,函数指针和再入函数有更多的挑战需要克服.主要由于函数变量的传递.典型的(绝大部分8051芯片)函数变量通过堆栈的入栈和出栈命令来传递. ...
- QT中使用函数指针
想仿命令行,所以定义了一个类,让一个String 对应一个 function,将两者输入list容器. 类中定义了 QString commandStr; void (MainWindow::*com ...
- Delphi中的函数指针判断是否为空
delphi函数指针 只有@@p才代表了函数指针本身的地址 assigned(p) 判断是否为空 或者用 @p=nil 来判断函数指针是不是为空 Delphi中的函数指针实际上就是指针,只是在使用 ...
- C++中使用函数指针 【瓦特芯笔记】
在C++类中使用函数指针. 类型定义: typedef 返回类型(类名::*新类型)(参数表) //类定义 class CA { public: char lcFun(int a) ...
- C语言结构体中的函数指针
这篇文章简单的叙述一下函数指针在结构体中的应用,为后面的一系列文章打下基础 本文地址:http://www.cnblogs.com/archimedes/p/function-pointer-in ...
- C 中typedef 函数指针的使用
类型定义的语法可以归结为一句话:只要在变量定义前面加上typedef,就成了类型定义.这儿的原本应该是变量的东西,就成为了类型. int integer; //整型变量int *pointer ...
- C++中的函数指针和指针函数
C++中的函数指针和指针函数 数组名一般可以被当成指向数组第一个元素的常量指针,同样的情况,在函数中,函数名可以本当成指向函数的常量指针,假如一个函数已经定义,那么它在计算机中一定有特定的 ...
- C语言中的函数指针
C语言中的函数指针 函数指针的概念: 函数指针是一个指向位于代码段的函数代码的指针. 函数指针的使用: #include<stdio.h> typedef struct (*fun_t ...
随机推荐
- Ubuntu 12.04 SSH 安装
By default Ubuntu Desktop OS comes with ssh clientpackage. It does not include ssh server package wh ...
- ORA-00911无效字符报错
今天在修改缺陷时遇到一个问题,更新数据库字段时一直报错:ORA-00911.sql脚本如下: '; '; '; 该脚本在数据库中可以执行,但是从程序中去访问数据库修改值时就会报错. 报错的原因在于,更 ...
- Android与OpenCV——重新下载安装和OpenCV匹配的Android开发环境
Android与OpenCV——重新下载安装和OpenCV匹配的Android开发环境 !!OpenCV4Android开发之旅(一)----OpenCV2.4简介及 app通过Java接口调用Ope ...
- ava中拦截器 过滤器 监听器都有什么区别
过滤器,是在java web中,你传入的request,response提前过滤掉一些信息,或者提前设置一些参数,然后再传入servlet或者struts2的action进行业务逻辑,比如过滤掉非法u ...
- Win XP 如何禁用系统的自动更新
想关闭系统的自动更新. 打开[控制面板]/[安全中心],发现“自动更新”和“更改安全中心通知我的方式”,都已成了灰色,无法更改. 网上查了一下,找到了这样一个处理方法:将[服务]中一个名为“Autom ...
- ubuntu10.04共享文件夹
ubuntu10.04共享文件夹 参考http://jingyan.baidu.com/album/9989c746084c70f648ecfe99.html,共享了home文件夹,然后把共享文件夹映 ...
- ssh传输出现encountered 1 errors during the transfer解决办法
以下方法简单排序,从简单到复杂: 法一:在SSH Secure File Transfer(上传文件那个),打开“Operation”菜单,打开“File Transfer Mode”子菜单,再选择“ ...
- CSS处理溢出
如果内容超过的区块的大小,内容就会溢出,可以使用下面的方法控制溢出 overflow visible 不剪切内容也不添加滚动条 auto 在必需时对象内容才会被裁切或显示滚动条 hidden 不显示超 ...
- C#发送手机验证码
C#发送手机验证码,平台有很多,我就说说其中的1个平台 测试环境:.net2.0 测试效果:速度还可以,10秒内接收短信 1.去http://www.yuntongxun.com注册,会送8元测试金额 ...
- Hide/Show running Console
http://stackoverflow.com/questions/3571627/show-hide-the-console-window-of-a-c-sharp-console-applica ...
