0
点赞
收藏
分享

微信扫一扫

函数指针和函数指针数组

幺幺零 2022-03-30 阅读 184

一、函数指针的声明和调用

1.指针声明:

函数指针顾名思义就是一个指向函数的指针。

int Add(int x,int y)
{
    return x+y;
}
char* Sub(char*)
{
    
}
//声明函数指针并初始化
int (*Add)(int ,int ) ptr=&Add;

char* (*Sub)(char*) prt_char=⋐

这里声明了两个函数指针 ptr和ptr_char指向了函数的地址,这里会发现Add取地址(&ADD),同样是原类型加上一个*,就是 int(*Add)(int,int),注意不是int *Add(int,int)。

对于一个返回指针的函数来说也是一样,Sub取地址(&Sub)原类型加上一个*,就是char*(*Sub)(char*),注意不是char* *Sub(int,int);

PS:声明的指针的时候,函数的返回值和参数类型、个数都要对的上。

对于函数来说取地址Add  (&Add),和直接写上本身是一样的(Add)。

所以初始化的时候也可以写成

int Add(int x,int y)
{
    return x+y;
}

int (*Add)(int,int)pf=Add;

 这种写法和上面等价。

 2.指针函数的调用:

可以通过使用函数指针调用函数。

int Add(int x,int y){
    return x+y;
}
int (*pf)(int,int)=&Add;
int ret=(*pf)(2,3);    //等价于int ret=Add(2,3);
printf("%d\n",ret);

 这里用指针调用函数的结果,跟直接使用函数的结果是一样的。

        因为上面&Add和Add的地址是一样的,所以这里导致了,不管解引用了几次pf,得到的结果都是函数Add。

二、函数指针数组

就一个数组,里面存储的类型是,指向函数的指针。

声明:

int Add(int x,int y){    //声明函数
    return x+y;
}
int Sub(int x,int y){
    return x-y;
}
int Mul(int x,int y){
    return x*y;
}
int Div(int x,int y){
    return x/y;
}

int (*pf1)(int,int)=Add;    //声明初始化函数指针
int (*pf2)(int,int)=Sub;
int (*pf3)(int,int)=Mul;
int (*pf4)(int,int)=Div;
//函数指针数组
int (*pf[4])(int,int)={Add,Sub,Mul,Div};    //初始化函数指针数组
//调用
for(int i=0;i<4;i++){    //通过数组元素调用函数
    pf[i](2,5);
}

        这里pf先跟[4]结合,说明了pf是个数组,然后去掉pf[4],剩下的int(*)(int,int)就是数组里面存储的类型,这个类型就是函数指针。通过调用数组不同的元素就能调用到不同的函数。 

既然是个数组,当然也可以定义一个指针,指向这个数组,一个指向函数数组的指针

类型的写法就是取地址pf  (&pf),原来的类型加上一个*,就是int  (  *( *pf[4] ) )(int ,int)。注意不是int* ( *pf[4] )(int,int)

int *(pf[4])(int,int);
int (*(*ptr[4]))(int,int)=&pf;

PS:要注意函数数组的指针取地址得到的就不是本身了。 

三.回调函数 

1.定义

回调函数就是利用函数指针,来在函数内部调用不同的函数。

void test()
{
	printf("hehe!\n");
}

void print_hehe(void (*pfun)())  //这个函数就叫回调函数
{
    if(1)
        pfun();
}

int main()
{
    print_hehe(test);
}

print_hehe的形参是一个函数指针,只要给函数不同的函数指针的实参,就能调用不同的函数。

而这里print_hehe就是一个回调函数。

 2.实例:

//简单的计算器实现
int Add(int x,int y){
    return x+y;
}
int Sub(int x,int y){
    return x-y;
}
int Mul(int x,int y){
    return x*y;
}
int Div(int x,int y){
    return x/y;
}

void calc(int(*fun)(int,int))
{
    int x,y;
    scanf("%d%d",&x,&y);
    int ret=fun(x,y);
    printf("%d\n",ret);
}

int main()
{
	int input=0;
    scanf("%d",&input);
    while(input){
        switch(input){
            case 1:
                calc(Add);
                break;
            case 2:
                calc(Sub);
                break;
            case 3:
                calc(Mul);
                break;
            case 4:
                calc(Div);
                break;
    	}
    }
    return 0;
}

 这种写法不仅能减少函数冗余,提高代码复用性,而且每次修改和添加代码增加删减功能的时候,修改的地方少,减少了函数代码的耦合度。

 函数指针数组的写法:

int Add(int x, int y) {
    return x + y;
}
int Sub(int x, int y) {
    return x - y;
}
int Mul(int x, int y) {
    return x * y;
}
int Div(int x, int y) {
    return x / y;
}

void menu()
{
    printf("**** 1.加法   2.减法   ****\n");
    printf("**** 3.乘法   4.除法   ****\n");
    printf("**** 0.退出   ****\n");
}

int main()
{
    int (*p[])(int, int) = { 0,Add,Sub,Mul,Div };
    int input = 1, x = 0, y = 0;
    menu();
    printf("请选择:>\n");
    while (input) {
        scanf("%d", &input);
        printf("请输入要计算的两个数:>\n");
        scanf("%d %d", &x, &y);
        int ret = p[input](x, y);
        printf("%d\n", ret);
    }
    
    return 0;
}

 

四.qsotr函数的解析


举报

相关推荐

函数指针数组

0 条评论