一直以来对C++成员函数指针没有太注意, 以为跟普通函数指针差不多, 使用起来才发现错误多多, 将成员函数指定当普通函数指针来使用了, 因此, 特意写了个小例子来帮助理解, 具体代码如下:
view plaincopy to clipboardprint?
·········10········20········30········40········50········60········70········80········90········100·······110·······120·······130·······140·······150
class FuncPointer
{
public:
void TestFunc1()
{
printf("call TestFunc1\r\n");
m_Fun = FuncPointer::TestFunc2;
(this->*m_Fun)();
}
void TestFunc2()
{
printf("call TestFunc2:\r\n");
}
static void TestFunc3()
{
printf("call TestFunc3:\r\n");
}
public:
typedef void (*Fun)();
typedef void (FuncPointer::*MFun)();
MFun m_Fun;
};
class FuncPointer1
{
public:
typedef void (FuncPointer::*MFun)();
MFun m_Fun;
};
typedef void (*G_Fun)();
void G_TestFun()
{
printf("call G_TestFun:\r\n");
}
int _tmain(int argc, _TCHAR* argv[])
{
// 调用静态函数
G_Fun fun1 = &FuncPointer::TestFunc3; // &符号可以不加
fun1();
// 调用非静态函数
//G_Fun fun2 = &FuncPointer::TestFunc1; // 编译失败, 不能将void (FuncPointer::* )(void)转换为G_Fun
//FuncPointer::Fun fun3 = &FuncPointer::TestFunc1; // 无法从void (__thiscall FuncPointer::* )(void)”转换为“FuncPointer::Fun
FuncPointer::Fun fun4 = FuncPointer::TestFunc3;
fun4();
FuncPointer::Fun fun5 = G_TestFun;
fun5();
//FuncPointer::MFun fun6 = G_TestFun; // 无法从"void (__cdecl *)(void)"转换为"FuncPointer::MFun"
FuncPointer::MFun fun7 = FuncPointer::TestFunc1;
//fun7(); // 项不会计算为接受 0 个参数的函数
FuncPointer* fp = new FuncPointer();
(fp->*fun7)(); // fp->(*fun7)() 出错
fp->m_Fun = FuncPointer::TestFunc2;
//(fp->*m_Fun)(); // m_Fun未声明
(fp->*(fp->m_Fun))();
FuncPointer1* fp1 = new FuncPointer1();
fp1->m_Fun = FuncPointer::TestFunc2;
(fp->*(fp1->m_Fun))();
return 0;
}
class FuncPointer
{
public:
void TestFunc1()
{
printf("call TestFunc1\r\n");
m_Fun = FuncPointer::TestFunc2;
(this->*m_Fun)();
}
void TestFunc2()
{
printf("call TestFunc2:\r\n");
}
static void TestFunc3()
{
printf("call TestFunc3:\r\n");
}
public:
typedef void (*Fun)();
typedef void (FuncPointer::*MFun)();
MFun m_Fun;
};
class FuncPointer1
{
public:
typedef void (FuncPointer::*MFun)();
MFun m_Fun;
};
typedef void (*G_Fun)();
void G_TestFun()
{
printf("call G_TestFun:\r\n");
}
int _tmain(int argc, _TCHAR* argv[])
{
// 调用静态函数
G_Fun fun1 = &FuncPointer::TestFunc3; // &符号可以不加
fun1();
// 调用非静态函数
//G_Fun fun2 = &FuncPointer::TestFunc1; // 编译失败, 不能将void (FuncPointer::* )(void)转换为G_Fun
//FuncPointer::Fun fun3 = &FuncPointer::TestFunc1; // 无法从void (__thiscall FuncPointer::* )(void)”转换为“FuncPointer::Fun
FuncPointer::Fun fun4 = FuncPointer::TestFunc3;
fun4();
FuncPointer::Fun fun5 = G_TestFun;
fun5();
//FuncPointer::MFun fun6 = G_TestFun; // 无法从"void (__cdecl *)(void)"转换为"FuncPointer::MFun"
FuncPointer::MFun fun7 = FuncPointer::TestFunc1;
//fun7(); // 项不会计算为接受 0 个参数的函数
FuncPointer* fp = new FuncPointer();
(fp->*fun7)(); // fp->(*fun7)() 出错
fp->m_Fun = FuncPointer::TestFunc2;
//(fp->*m_Fun)(); // m_Fun未声明
(fp->*(fp->m_Fun))();
FuncPointer1* fp1 = new FuncPointer1();
fp1->m_Fun = FuncPointer::TestFunc2;
(fp->*(fp1->m_Fun))();
return 0;
}
从代码可以看出成员函数指针使用需注意以下几个方面:
1. 不管是在类中或外部定义, 必须为 (class::*fun)(param...) 格式, 否则为一般的函数指针
2. 函数指针的取地址符&可有可无
3. 静态成员函数相当于普通函数, 可用于普通函数指针, 而普通成员函数则不能
4. 成员函数指针的调用一定需要借用类实例来完成
5. 类实例不能直接调用自己内部定义的成员函数指针, 调用方式: (instanse->*(instanse->m_fun))()