精通Cocos2d-x游戏开发(基础卷)
上QQ阅读APP看书,第一时间看更新

4.4 函数指针

函数指针指向一个函数的地址,通过函数指针可以调用函数,而在Cocos2d-x中的回调函数,就是用了函数指针来实现的。下面先来看一个简单的例子。

//Log函数
void Log(const char* msg)
{
    printf("%s\n", msg);
}
//赋值函数指针fun
void (*fun)(const char*)= Log;
//执行函数指针
(*fun)("abc");

上面的代码简单地展示了函数指针的使用,首先声明一个函数指针fun,然后让该函数指针指向Log函数,最后使用函数指针来调用Log函数,这里只要知道函数指针怎么写就可以了。通过对比Log函数可以发现,它们只有一点不同,就是Log换成了(*fun)。这种写法是定义了一个变量,变量的名字是fun,而变量的类型是void (*)(const char*),可以将符合该函数原型的任意函数赋值给它,然后调用这个函数,例如,注册一个回调函数,在接收到服务端发送的数据时,调用该回调函数进行处理,在不同的情况下可以注册不同的回调函数,而不需要在调用的地方写一大堆代码。

前面介绍的是普通函数的写法,平时用得较多的还是类的成员函数。类的成员函数与普通函数是不一样的写法,因为成员函数比普通函数多了对象的概念,可以在成员函数里使用this指针,如果没有this指针则不行。

class A
{
public:
    void Log(const char* msg)
    {
        printf("%s\n", msg);
    }
};
 //定义fun成员函数变量
void (A::*fun)(const char*) = &A::Log;
//创建一个A对象
A aa;
//执行成员函数
(aa.*fun)("a");
(&aa->*fun)("b");

上面的代码定义了一个类A,该类有一个public的成员函数Log,首先定义了一个A的成员函数指针fun,注意这里的写法与前面的普通函数不同,在*fun前面加A::表示这个函数是A的成员函数,然后再定义函数的原型,并将A::Log的地址赋给它,这时fun指向的是A::Log的地址。但这还不够,还需要一个对象,所以接下来定义了一个对象a。

与普通函数调用不同的是*fun前面对应加了这个对象,切记看清楚括号的范围,忘记加括号或者括号弄错,则将编译不过。在这里既可以使用对象、方法来调用成员函数指针,也可以用指针->来访问。