指针-----函数指针

来源:互联网 发布:idea mac 激活服务器 编辑:程序博客网 时间:2024/06/05 20:45
 
指针-----函数指针
2010-09-07 17:05

函数指针的声明:

函数指针包括两部分信息:

1).函数本身的内存地址

2).函数参数和返回值类型信息

因此,声明一个函数需要包括以下三部分内容:

1)函数返回值类型

2)指向函数的函数指针名

3)函数参数类型列表

函数指针声明通式:

       return_type (*fun_pointer_name)([parameter1_type],[parameter2_type],...);

注意:要与下式区分开来:

return_type *fun_pointer_name(para1_type,para2_type,...);//这个是一个函数声明,声明返回一个指针的函数

函数指针的初始化:

       与普通的指针变量的初始化一样。

注意:不能对未初始化的函数指针进行函数调用操作。对未初始化的函数指针进行作操作是危险的(当然赋值操作除外^_^)

建议:在声明一个指针时,就立即将它初始化为NULL。(这样是不是应该叫定义了^_^

函数指针的赋值:

直接将与函数名赋值给函数指针名就可以。如下:

       int sum(int a,int b)

       {

              return a+b;

       }    

      

       void main()

       {

              int (*funPtrSum)(int,int);//声明函数指针funPtrSum,并未初始化

              int x=10,y=50,z=0,;

              funPtrSum=sum;

              z=funPtrSum(x,y);

       }

函数指针的使用:    

1) 如同普通的函数调用那样用来作直接调用函数  

函数指针名(函数参数列表);

2)作为函数参数

函数指针也可以作为函数参数,这样函数可以通过这个指针参数对它所指向的函数进行调用。这时,我们在调用这个有函数指针参数的函数时,把这个指针所向的函数名传进去就可以了。如下:

              int callSum(int (*pPtrSum)(int,int),int x);    

              z=callsum(sum(x,y),z);

      

3)函数数组

声明格式如下:

       array_type (*function_pointer_array_name[elements_num])(function_parameter_type_list);

也可以如下定义:

       array_type (*function_pointer_array_name[elements_num])(function_parameter_type_list)=

       {function_name0,function_name1,...};

另外插入一点关于数组作函数参数的内容:

如果把数组作为参数传递且在函数中需要用到这个数组的元素个数时,应把数组的元素个数作另一个参数传递。

测试的示例代码如下测试的示例代码如下:

int sum(int a,int b)
{
return (a+b);
}

int sub(int a,int b)
{
return a-b;
}

char cs(char a,char b)
{
return a+b;
}

char csub(char a,char b)
{
return a+b;
}

int callSum(int (*pPtrSum)(int,int),int pArr[],int length);
//int callSum(int (*pPtrSum)(int,int),char pArr[]);

int _tmain(int argc, _TCHAR* argv[])
{
int x=10,y=50,z=0;
int arr[5]={1,2,3,4,5};
int len=sizeof(arr)/sizeof(int);

//函数指针的声明或定义:
int (*funPtrSum)(int,int);//声明函数指针funPtrSum,并未初始化 这里funPtrSum里是一个无效的随机值

//如下函数指针的声明方法是错误的:
//int *funPtrSum(int,int);//这是声明返回int指针类型值的函数,而非声明一个函数指针

//也可以如下这样直接定义
//int (*funPtrSum)(int,int)=NULL; 这是一种比较安全的做法



//函数指针的赋值
funPtrSum=sum;   //给函数指针赋值,使该指针指向函数sum()



//函数指针的使用:
//1)如同普通的函数调用
//z=funPtrSum(x,y); //错误!非法操作没有初始化的函数指针
z=funPtrSum(x,y); //使用函数指针,通过函数指针调用函数与直接用函数名调用函数实现相同的功能 z=60
z=sum(x,z);    //通过函数调用 z=70

//2)函数指针当作函数参数传递
//z=callSum(funPtrSum(x,y),z);//错误
z=callSum(funPtrSum,arr,len);//sum()函数的地址替代funPtrSum这个函数指针
// z=callSum(funPtrSum,arr);

//3)函数指针数组
int (*ptrFunSumArr[2])(int,int)={sum,sub};
z=ptrFunSumArr[0](x,y)+ptrFunSumArr[1](x,y);//z=20
z=0;
for(int i=0;i<2;i++)
{
   z+=ptrFunSumArr[i](x,y);
}
x=sizeof(ptrFunSumArr);//x=8
y=sizeof(ptrFunSumArr[0]);//y=4
z=x/y; //z=2

char (*ptrFunSumArr2[2])(char,char);
ptrFunSumArr2[0]=cs;
ptrFunSumArr2[1]=csub;
x=sizeof(ptrFunSumArr);//x=8
y=sizeof(ptrFunSumArr[0]);//y=4
z=x/y; //z=2

return 0;
}

//函数指针作为参数的函数
int callSum(int (*pPtrSum)(int,int),int pArr[],int len)
{
int i=0,total=0;

for(i=0;i<len;i++)
{
   if(i==len-1)
    total+=pPtrSum(pArr[i],0);
   else
    total+=pPtrSum(pArr[i],pArr[i+1]);
}

return total;//(pPtrSum(m,m));
}


//如果把数组作为参数传递且在函数中需要用到这个数组的元素个数时,应把数组的元素个数作另一个参数传递
//如果把上面的函数用如下函数实现,将出现一个问题:
//int callSum(int (*pPtrSum)(int,int),char pArr[])
//{
// int i=0,total=0;
// int ptemp=sizeof(pArr);
// ptemp=sizeof(char);
// int len=sizeof(pArr)/sizeof(pArr[0]);//这里得到的将不是数组的大小,且len==1 为什么?
//       //因为这里pArr只是一个数组指针,sizeof(pArr)是一个指针的大小而不是整个数组所分配空间的大小,其值为4,而sizeof(pArr[0])值也是4,
//       //所以len为1。如果把pArr[]改为char类型,那么这里的len值将是4(因为pArr[0]是char类型,sizeof(pArr[0])==1;)。
//       //所以在用数组作函数参数时,要把函数元素个数也作为另一个参数传递,如同上一个函
//       //数int callSum(int (*pPtrSum)(int,int),int pArr[],int len)那样。
//
//
// for(i=0;i<len;i++)
// {
//   if(i==len-1)
//    total+=pPtrSum(pArr[i],0);
//   else
//    total+=pPtrSum(pArr[i],pArr[i+1]);
// }
//
// return total;//(pPtrSum(m,m));