http://blog.csdn.net/maojudong/article/details/8194143
测试目录:
1.普通函数指针指向普通函数
2.普通函数指向非静态成员函数
3. 类外部的 类函数指针 指向普通函数
4. 类外部的 类函数指针 指向成员函数
5. 类内部的 函数指针 指向成员函数 (类似于第2条)
6. 类内部的 函数指针 指向普通函数
直接上代码:
- #include <iostream>
- #include <string>
- #include <vector>
- #include <map>
- using namespace std;
- class Foo
- {
- public:
- string m_str;
- Foo()
- {
- m_str = "";
- }
- static void testFunc2(int a)
- {
- cout<<"Foo:void testFunc2(int a)"<<endl;
- cout<<a<<endl;
- }
- void testFunc4(int a)
- {
- cout<<"Foo:void testFunc4(int a)"<<endl;
- cout<<a<<endl;
- }
- static void testFunc5(int a)
- {
- cout<<"Foo:void testFunc5(int a)"<<endl;
- cout<<a<<endl;
- }
- void (*pTestFunc5)(int a);
- void (*pTestFunc6)(int a);
- };
- void (*pTestFunc1)(int a);
- void (*pTestFunc2)(int a);
- void (Foo::*pTestFunc3)(int a);
- void (Foo::*pTestFunc4)(int a);
- void testFunc1(int a)
- {
- cout<<"func1 pointer test"<<endl;
- cout<<a<<endl;
- }
- void testFunc3(int a)
- {
- cout<<"func3 pointer test"<<endl;
- cout<<a<<endl;
- }
- void testFunc6(int a)
- {
- cout<<"func6 pointer test"<<endl;
- cout<<a<<endl;
- }
- int main(int argc, const char *argv[])
- {
- Foo foo;
- //foo.test("woo",100);
- pTestFunc1 = testFunc1; //经常用这个方法
- (*pTestFunc1)(1);
- pTestFunc2=&foo.testFunc2;
- (*pTestFunc2)(2);
- //pTestFunc3 = &testFunc3; //编译器报错,不可以这么使用
- pTestFunc4 = &Foo::testFunc4; //初始化的时候必须带有&Foo::
- //pTestFunc4(4);//编译器报错,不可以这么使用
- //foo.pTestFunc4(4);//编译器报错,不可以这么使用
- //foo.*pTestFunc4(4);//编译器报错,不可以这么使用
- //foo.(*pTestFunc4)(4);//编译器报错,不可以这么使用
- (foo.*pTestFunc4)(4); //正常运行
- foo.pTestFunc5=&Foo::testFunc5;
- foo.pTestFunc5(5);
- foo.pTestFunc6=&testFunc6;
- foo.pTestFunc6(6);
- return 0;
- }
程序分析:
1.普通函数指针指向普通函数
pTestFunc = &testFunc;
或者
pTestFunc = testFunc;
调用方式
pTestFunc(1)
(pTestFunc)(1)
(*pTestFunc)(1)
2.普通函数指向非静态成员函数
pTestFunc=foo.testFunc2; 编译器报错,提示不匹配
error: argument of type ‘void (Foo::)(int)’ does not match ‘void (*)(int)’
pTestFunc=&foo.testFunc2; 编译器报错,提示不匹配
error: ISO C++ forbids taking the address of a bound member function to form a pointer to member function. Say ‘&Foo::testFunc’
error: cannot convert ‘void (Foo::*)(int)’ to ‘void (*)(int)’ in assignment
pTestFunc=Foo::testFunc2; 编译器报错
error: invalid use of non-static member function ‘void Foo::testFunc(int)’
pTestFunc=&Foo::testFunc2; 编译器报错
error: cannot convert ‘void (Foo::*)(int)’ to ‘void (*)(int)’ in assignment
普通函数指向静态成员函数
pTestFunc = &testFunc;
或者
pTestFunc = testFunc;
调用方式
pTestFunc(1)
(pTestFunc)(1)
(*pTestFunc)(1)
2.普通函数指向非静态成员函数
pTestFunc=foo.testFunc2; 编译器报错,提示不匹配
error: argument of type ‘void (Foo::)(int)’ does not match ‘void (*)(int)’
pTestFunc=&foo.testFunc2; 编译器报错,提示不匹配
error: ISO C++ forbids taking the address of a bound member function to form a pointer to member function. Say ‘&Foo::testFunc’
error: cannot convert ‘void (Foo::*)(int)’ to ‘void (*)(int)’ in assignment
pTestFunc=Foo::testFunc2; 编译器报错
error: invalid use of non-static member function ‘void Foo::testFunc(int)’
pTestFunc=&Foo::testFunc2; 编译器报错
error: cannot convert ‘void (Foo::*)(int)’ to ‘void (*)(int)’ in assignment
普通函数指向静态成员函数
将代码更改一下后,将成员函数前加入一个static关键字
则下面的初始化方式编译和运行正常
pTestFunc2=Foo::testFunc2;
pTestFunc2=&Foo::testFunc2;
pTestFunc2=foo.testFunc2;
pTestFunc2=&foo.testFunc2;
调用方式和普通函数指向普通函数一致
pTestFunc2(2)
(pTestFunc)2(2)
(*pTestFunc)2(2)
3. 类外部的 类函数指针 指向普通函数
这种用法就是错误的,所以编译器不通过
pTestFunc3 = testFunc3; 编译器报错,
test5.cpp:83: error: cannot convert ‘void(int)’ to ‘void (Foo::*)(int)’ in assignmen
pTestFunc3 = &testFunc3;
test5.cpp:83: error: cannot convert ‘void (*)(int)’ to ‘void (Foo::*)(int)’ in assignmen
4. 类外部的 类函数指针 指向成员函数
初始化指针的方式
pTestFunc4 = &Foo::testFunc4; //初始化的时候必须带有&Foo::
pTestFunc4 = Foo::testFunc4; //编译器报错
pTestFunc4 = foo.testFunc4; //编译器报错
pTestFunc4 = &foo.testFunc4; //编译器报错
调用方式:
pTestFunc4(4);//编译器报错,不可以这么使用
foo.pTestFunc4(4);//编译器报错,不可以这么使用
foo.*pTestFunc4(4);//编译器报错,不可以这么使用
foo.(*pTestFunc4)(4);//编译器报错,不可以这么使用
(foo.*pTestFunc4)(4)//正常运行,所以必须要带有括号
如果foo为指针
Foo *foo=new Foo();
(foo->*pTestFunc4)(4)
5. 类内部的 函数指针 指向成员函数 (类似于第2条)
foo.pTestFunc5=foo.testFunc5; 编译器报错
test5.cpp:125: error: argument of type ‘void (Foo::)(int)’ does not match ‘void (*)(int)’
foo.pTestFunc5=&foo.testFunc5; 编译器报错
test5.cpp:123: error: ISO C++ forbids taking the address of a bound member function to form a pointer to member function. Say ‘&Foo::testFunc’
test5.cpp:123: error: cannot convert ‘void (Foo::*)(int)’ to ‘void (*)(int)’ in assignment
foo.pTestFunc5=Foo::testFunc5;编译器报错
foo.pTestFunc5=&Foo::testFunc5; 编译器报错
声明为静态函数后(与第2条相似),编译和运行都OK
foo.pTestFunc5=foo.testFunc5;
foo.pTestFunc5=&foo.testFunc5;
foo.pTestFunc5=Foo::testFunc5;
foo.pTestFunc6=&Foo::testFunc5;
6. 类内部的 函数指针 指向普通函数
编译和运行都OK
foo.pTestFunc2=testFunc6;
foo.pTestFunc2=&testFunc6;
则下面的初始化方式编译和运行正常
pTestFunc2=Foo::testFunc2;
pTestFunc2=&Foo::testFunc2;
pTestFunc2=foo.testFunc2;
pTestFunc2=&foo.testFunc2;
调用方式和普通函数指向普通函数一致
pTestFunc2(2)
(pTestFunc)2(2)
(*pTestFunc)2(2)
3. 类外部的 类函数指针 指向普通函数
这种用法就是错误的,所以编译器不通过
pTestFunc3 = testFunc3; 编译器报错,
test5.cpp:83: error: cannot convert ‘void(int)’ to ‘void (Foo::*)(int)’ in assignmen
pTestFunc3 = &testFunc3;
test5.cpp:83: error: cannot convert ‘void (*)(int)’ to ‘void (Foo::*)(int)’ in assignmen
4. 类外部的 类函数指针 指向成员函数
初始化指针的方式
pTestFunc4 = &Foo::testFunc4; //初始化的时候必须带有&Foo::
pTestFunc4 = Foo::testFunc4; //编译器报错
pTestFunc4 = foo.testFunc4; //编译器报错
pTestFunc4 = &foo.testFunc4; //编译器报错
调用方式:
pTestFunc4(4);//编译器报错,不可以这么使用
foo.pTestFunc4(4);//编译器报错,不可以这么使用
foo.*pTestFunc4(4);//编译器报错,不可以这么使用
foo.(*pTestFunc4)(4);//编译器报错,不可以这么使用
(foo.*pTestFunc4)(4)//正常运行,所以必须要带有括号
如果foo为指针
Foo *foo=new Foo();
(foo->*pTestFunc4)(4)
5. 类内部的 函数指针 指向成员函数 (类似于第2条)
foo.pTestFunc5=foo.testFunc5; 编译器报错
test5.cpp:125: error: argument of type ‘void (Foo::)(int)’ does not match ‘void (*)(int)’
foo.pTestFunc5=&foo.testFunc5; 编译器报错
test5.cpp:123: error: ISO C++ forbids taking the address of a bound member function to form a pointer to member function. Say ‘&Foo::testFunc’
test5.cpp:123: error: cannot convert ‘void (Foo::*)(int)’ to ‘void (*)(int)’ in assignment
foo.pTestFunc5=Foo::testFunc5;编译器报错
foo.pTestFunc5=&Foo::testFunc5; 编译器报错
声明为静态函数后(与第2条相似),编译和运行都OK
foo.pTestFunc5=foo.testFunc5;
foo.pTestFunc5=&foo.testFunc5;
foo.pTestFunc5=Foo::testFunc5;
foo.pTestFunc6=&Foo::testFunc5;
6. 类内部的 函数指针 指向普通函数
编译和运行都OK
foo.pTestFunc2=testFunc6;
foo.pTestFunc2=&testFunc6;