1、定义
void (*pfun)();
void (*pfun)(int)
void (*pfun)(int x)
2、使用
void add(int x)
{
}
pfun = add;
pfun(x)
(*pfun)(x);
3、重新定义类型
typedef void(*FunP)(int); //定义新的类型
FunP fun; //定义一个变量
void myfun(int x)
{
}
fun=MyFun; //指向一个函数
fun(x); //调用执行
4、作为参数传递
void MyFun1(int x);
typedef void (*FunType)(int );
void CallMyFun(FunType fp,int x);
int main(int argc, char* argv[])
{
CallMyFun(MyFun1,10);
}
void CallMyFun(FunType fp,int x)
{
fp(x);
}
void MyFun1(int x)
{
printf(“函数MyFun1中输出:%d
”,x);
}
函数指针数组引入
int *a()[10]; //指针数组,数组的包含了10个int *类型的成员函数。
int (*parr1[10])(); //函数指针数组
int (*a)[10]; //数组指针,a指向了一个包含有10个int型数据的数组
int (*arr[5])(int ,int)={Add,Sub,Mul,Div}; //先定义一个函数指针数组:里面有+-*/四个方法
int (*(*p)[5])(int ,int)=&arr; //定义一个指向函数指针数组的指针
https://blog.csdn.net/daboluo521/article/details/79946214
https://www.cnblogs.com/tp-16b/p/7860491.html#_label3
函数指针的强制转化
#include<stdio.h>
void fun()
{
printf("it is a test %x.
",fun);
}
void main(void)
{
int (*pfun)();
//将fun强转并调用
( ( int (*)() )fun)();
( *( int (*)() )fun)();
//将fun强转赋值给另一函数指针
pfun = ( int (*)() )fun;
pfun();
(*pfun)();
//直接用函数地址这个实数去转化
( ( int (*)() )0x400526)();
( *( int (*)() )0x400526)();
pfun = ( int (*)() )0x400526;
pfun();
(*pfun)();
//把实数地址转为void *类型呢
( ( void (*)() )0x400526)();
( *( void (*)() )0x400526)();
pfun = ( void (*)() )0x400526; //此处应避免这种做法,不同类型间的赋值.
pfun();
(*pfun)();
//实数转为void *
void *p ;
int *q;
p = (void *)0x400526;
q = (void *)0x400526; //此处应避免这种做法,void 赋给其他类型,应做强制转化.gnu下会出现警告.
//p++; //对void 类型的指针不能做算法
}
if 0
void 译为无类型,空类型
从int * 到 char *的转化不兼容,但是编译能通过。
任何类型指针都可以赋值给void指针,但是反之不行。也就是说,如果需要void指针类型转化成其他指针类型,需要将此NULL类型强制转换。
void指针不能进行算法操作,因为ANSI标准规定:能进行算法操作的指针必须是确定其指向的数据类型的大小的。
能够确定指向的数据类型的指针可以运算是因为,例如:指针p,那么指针p++,就是对p的地址增加p所指向的数据类型那么大小的长度。所以,
如果有一个指针你不知道它指向的数据类型的大小,那么再做p的运算的时候,比如p++,就不知道到底要在p原来的地址上增加多少个长度?
这种不确定就产生了相应的规则:不明确指向的数据类型的void指针不能进行运算。