函数: void (*signal (int sinno,void(*func)(int)))(int)
上述函数该如何读呢? 那么先了解下面的一组概念
指针函数:
本质是一个函数,其返回值为指针。
函数指针:
本质是一个指针,其指向一个函数。
如果想详细更进一步的了解,可以参考下述文章: 函数指针和指针函数用法和区别
指针函数:
简单的来说,就是一个返回指针的函数,其本质是一个函数,而该函数的返回值是一个指针
以下示例:
int fun(int x,int y);
这种函数应该都很熟悉,其实就是一个函数,然后返回值是一个 int 类型,是一个数值int *fun(int x,int y);
这个函数就是一个指针函数。其返回值是一个 int 类型的指针,是一个地址。总结: 指针函数和普通函数对比不过就是其返回了一个指针(即地址值)而已
函数指针:
其本质是一个指针变量,该指针指向这个函数。总结来说,函数指针就是指向函数的指针。
以下示例:
int fun(int x,int y);
普通函数int *fun(int x,int y);
指针函数int (*fun)(int x,int y);
函数指针函数指针是需要把一个函数的地址赋值给它,有两种写法:
fun = &Function;
fun = Function;
取地址运算符&不是必需的,因为一个函数标识符就表示了它的地址,如果是函数调用,还必须包含一个圆括号括起来的参数表。
调用函数指针的方式也有两种:
x = (*fun)();
x = fun();
两种方式均可,看个人习惯,如果理解其定义,随便怎么用都行
void (*signal(int sig, void (*func)(int)))(int) void (*func)(int) = A func 是一个指向函数的指针--该函数以int作为入参,返回值为空 signal(int sig, void (*func)(int)) = B signal 是一个函数-- 该函数有两个参数(一个是int型变量 sig 一个是指向函数的指针A) void (*B)(int) B是一个函数,返回值是一个指向函数(入参为int 返回值为空)的指针 signal 是一个函数-- 该函数有两个参数(一个是int型变量 sig 一个是指向函数(该函数以int作为入参,返回值为空 )的指针) ,signal的返回值是一个指向函数(入参为int 返回值为空)的指针
函数指针,一般用途作为“回调函数”使用。
比如写了一个方法(函数),你希望调用它执行完处理之后,自动调用另一个后续的函数来处理继续的业务。
这个时候就可以把 “一个函数的入口地址”当是一个指针。 你的处理方法中接受函数参数时把这个指针传进来。
// 指针函数 int *myPlus(int a, int b) {
printf("plus:%d + % d = %d\n" ,a ,b, a + b ); return 0; } int *myMinus(int a, int b) {
printf("minus: %d - % d = %d\n", a, b, a - b); return 0; } //参数funtz int funt2( int a, int b , void *funtz) {
//pf为函数指针, int(*pf)(int, int) = ( int (*)(int,int ) )funtz; pf(a, b); return 0; } //主函数入口 int main() {
funt2(10,20, myPlus); //myPlus 是一个函数指针,它现在是作为一个参数在传递 funt2(10,20, myMinus); return 0; }
函数
: 本质是一段可执行代码段。函数名:
指向这段代码段的首地址。函数在内存中是有地址的,函数名对应着函数的首地址,既然有地址,就可以定义指针储存地址或更改指针的指向,存储函数(首)地址的指针,称为函数指针
#include<stdio.h> void print() {
printf("调用了print函数\n"); return; } int main() {
((void (*)(void))0x00)(); return 0; }
结果:
调用了print函数
#include<stdio.h> int main() {
int a=100; //a的地址是0x0061fefc printf("打印a:%d\n",*(int*)0x0061fefc); return 0; }
结果:
打印a:100
#include<stdio.h> void print() {
printf("调用了print函数\n"); return; } int main() {
int a=100; printf("第一次打印a:%d\n",a); printf("a的地址是:%p\n",&a); //a的地址是0x0061fefc printf("第二次打印a:%d\n",*(int*)0x0061fefc); printf("\n"); print(); printf("print的地址是:%p\n",print); //print()的地址是0x00 ((void(*)(void))0x00)(); return 0; }
结果:
第一次打印a:100 a的地址是:0061fefc 第二次打印a:100 调用了print函数 print的地址是:00 调用了print函数
#include<stdio.h> void print() {
printf("调用了print函数\n"); return; } int main() {
//void (*p)(void)函数类型的基本格式 //第一种玩法 ((void (*)(void))0x00)(); //第二种玩法 void (*p1)(void)=print; p1(); //第三种玩法(不推荐) void (*p2)(void)=&print; (*p2)(); //第四种玩法 typedef void (*PF)(void); PF pf=print; pf(); return 0; }
结果:
调用了print函数 调用了print函数 调用了print函数 调用了print函数