一、函数指针的基础知识
- 定义:如果在程序中定义了一个函数,那么在编译时系统就会为这个函数代码分配一段存储空间, 这段存储空间的首地址称为这个函数的地址 。 而且函数名表示的就是这个地址。既然是地址我们就可以定义一个指针变量来存放,这个指针变量就叫作 函数指针变量 ,简称 函数指针 。
二、函数指针的声明
- 声明格式:函数返回值类型 (* 指针变量名) (函数参数列表);
例如:
#include <stdio.h>
int add(int num1, int num2);
int add(int num1, int num2) {
return num1 + num2;
}
int main() {
//声明指针函数变量:函数返回值类型 (* 指针变量名) (函数参数列表);
int (*p)(int, int);
return 0;
}
三、函数指针在程序中的使用
上面我们介绍了函数指针变量的声明,接下来我们来对函数指针进行使用。
#include <stdio.h>
int add(int num1, int num2);
int sub(int num1, int num2);
//函数指针变量做形参
int way(int num1, int num2, int (*p)(int num3, int num4));
int way(int num1, int num2, int (*p)(int num3, int num4)) {
return p(num1, num2);
}
int sub(int num1, int num2) {
return num1 - num2;
}
int add(int num1, int num2) {
return num1 + num2;
}
int main() {
int a = 9;
int b = 4;
int result;
int (*p)(int, int);
p = add;
result = p(a, b);
printf("第一次加法使用:%d\n", result);
p = sub;
result = p(a, b);
printf("第二次减法使用:%d\n", result);
result = way(a, b, add);
printf("第三次使用:%d\n", result);
return 0;
}
四、基于汇编层次的讲解
主要讲解在代码注释里面
//该语句是将函数add的首地址赋值给p:
mov DWORD PTR _p$[ebp], OFFSET FLAT:_add
//下面这四句就是将实参赋值给形参
mov eax, DWORD PTR _b$[ebp]
push eax
mov ecx, DWORD PTR _a$[ebp]
push ecx
/*
下面这条语句可以看出,调用p,使用的是call指令,也就证明了p变量的使用,
本质上还是对函数的调用
*/
call DWORD PTR _p$[ebp]
add esp, 8