指针知识梳理7- 函数指针
一、函数的地址
前面讲 程序运行起来以后,在内存中有代码区,程序运行每一条指令,是从内存中读出来这条指令,然后再运行。所谓函数的地址是指函数的入口地址,这个函数的从这个地址開始进入运行,也就是从这个地址处取指令运行。
那么在代码层面,函数的地址用 函数指针变量 来存储。
二、基本使用
1、函数指针定义
函数指针的定义,在语法看起来略微有点怪,仅仅须要记住形式返回值 (*指针变量名)(形參类型);
比方,下面4个函数
void func1(void)
{
}
int func2(void)
{
}
int func3(int a)
{
}
int func4(int a,int b)
{
}
int func5(int a,int b)
{
}
能够定义例如以下指针变量来记录其地址,注意指针变量的类型一定要跟函数匹配。
void (*p1)(void); int (*p2)(void); int (*p3)(int); int (*p4)(int,int);
2、取函数的地址
函数的地址有两种方法获得 &函数名 或者 直接函数名,两种方式等效。
p1 = &func1; p2 = &func2; p3 = &func3; p4 = &func4; //下面等效于上面 p1 = func1; p2 = func2; p3 = func3; p4 = func4;
3、通过指针调用函数
通过指针变量去调用函数,也有两种方式,有* 和没 *都能够。(1)跟函数调用方式一样,把函数名换成 变量名。
p1(); p2(); p3(1); p4(1,2);
(2)跟函数调用方式一样,把函数名换成 (*变量名)。
(*p1)(); (*p2)(); (*p3)(1); (*p4)(1,2);
測试例如以下代码:
#include <stdio.h>
void func1(void)
{
printf("this is func1\n");
}
void func2(void)
{
printf("this is func2\n");
}
int add(int a,int b)
{
printf("this is add\n");
return a+b;
}
int sub(int a,int b)
{
printf("this is sub\n");
return a-b;
}
int main()
{
void (*p1)(void);
int (*p2)(int,int);
int ret = 0;
p1 = func1;
p1();
(*p1)();
p1 = &func2;
p1();
(*p1)();
p2 = add;
ret = p2(1,2);
printf("ret = %d\n",ret);
ret = (*p2)(1,2);
printf("ret = %d\n",ret);
p2 = ⊂
ret = p2(1,2);
printf("ret = %d\n",ret);
ret = (*p2)(1,2);
printf("ret = %d\n",ret);
return 0;
}
四、typedef 与函数指针
在以上代码中,函数指针的定义的写法是比較麻烦的,通常我们用typedef 为这样的类型取别名。typedef void (*type1)(void); typedef int (*typ2)(void); typedef int (*type3)(int); typedef int (*type4)(int,int); void (*p1)(void); int (*p2)(void); int (*p3)(int); int (*p4)(int,int);
比較以上两种写法,基本上一样,当有typedef的时候是在定义新的类型。
type1 type2 type3 type4 是类型。
p1,p2,p3,p4 是变量。
type1 p1; //等效于 void (*p1)(void); type2 p2; //等效于 int (*p1)(void); type3 p3; //等效于 int (*p3)(int); type4 p4; //等效于 int (*p4)(int,int);
浙公网安备 33010602011771号