C语言工作笔记-对函数指针的进一步认识(与回调函数结合使用,并且对比C++的回调)
目录
背景和基本概念(含与C++回调对比)
函数指针最一般的用法
函数指针结合回调
源码打包
背景和基本概念(含与C++回调对比)
毕业也有10个月了,加上实习已经工作14个月了,感觉这一年多的板砖生涯学到了很多的东西。同样本人对函数指针又有了新的认识。原因是这个月在某平台上进行二次开发,发现这里面有很多的callback!这个callback并不是C++里的callback,而是C语言的Callback。
估计是开发这个平台的人喜欢C语言的Callback,而不喜欢C++的Callback。
这里我简单说明下我对这两种Callback体会:
在我这边的项目中,我接触过2种不同的回调!
一种是C语言的,他的回调方式是使用函数指针。通常会有一个注册函数,把要回调的函数注册进去,之后就通过函数指针进行调用,这种是我最近才接触到的。
还有一种回调是C++的回调。这个在项目里面接触得比较多,毕竟现在我就是C++开发工程师(虽然有时候也做Java和DBA的工作),这种回调感觉比C语言的回调更加的灵活。这种一般是类继承的概念,一般用纯虚类使用纯虚函数充当接口(也有用一般的类,用虚函数做接口的),用虚函数的特点使用父类指针调用子类对象。感觉C++的回调,还是比C语言灵活的。
下面将说明下C语言中函数指针结合回调函数的用法;
函数指针最一般的用法
下面给出函数指针最一般的用法,估计稍微学过C语言语法的学生都会使用:
#include <stdio.h>int Sum(int a, int b){return a + b;
}int main(int argc, int **argv){int (*pFun)(int a, int b);pFun = Sum;printf("Sum=%d\n", pFun(100, 200));getchar();return 0;
}
运行截图如下:
但这样的函数指针并不能提现他真正方便的地方!
下面说下他正在方便的地方!
函数指针结合回调
这里其实可以把函数指针理解为变量,如下代码:
int (*fun1)(char);
int *(*fun2)(char);
int (*fun3[])(char);
int *(*fun4[])(char);typedef int(*pProcFun)(char);
pProcFun pFun1;
pProcFun pFun3[];
pProcFun *pFun3ptr;
pProcFun pFun2;
pProcFun pFun4[];
pProcFun *pFun4ptr;
如下最基础的,模块注册,模块管理,根据函数指针回调的例子!
运行截图如下:
程序结构如下:
源码如下:
FirstModule.h
#pragma once
#include "stdef.h"
#include "moduleAdmin.h"int InitFirstModule();
moduleAdmin.h
#pragma once#include "stdef.h"typedef enum tagMODULE_SETS //SETS表示这是枚举集合
{MY_ALL_MODULE = 0,MY_READ_MODULE = 1,MY_WRITE_MODULE = 2,MY_INVALID_MODULE = 0xffff}MODULE_SETS_E; //E表示enumtypedef int(*pProcFun)();typedef struct tagMoudleData //一般带有管理的结构体在C语言中都是tagXXXX
{int iModule; //每个模块唯一IDpProcFun pFun;
}MOUDLE_DATA_S; //一般在结构体结尾都加S,代表struct;int RegisterProc(int iModule, pProcFun pFun);
int ExcuteAllModule();
SecondMoudle.h
#pragma once#include "stdef.h"
#include "moduleAdmin.h"int InitSecondModule();
stdef.h
#pragma once#include <stdio.h>
#include <Windows.h>#define OK 0
#define ERR -1
FirstModule.cpp
#include "FirstModule.h"int FirstModuleProc(){printf("Hello I am First Module\n");return OK;
}int InitFirstModule(){RegisterProc(MY_WRITE_MODULE, FirstModuleProc);return OK;
}
main.cpp
#include "stdef.h"
#include "FirstModule.h"
#include "SecondModule.h"DWORD WINAPI MyThread(){while(1){ExcuteAllModule();Sleep(1000);}
}int TestFunPtr(){InitFirstModule();HANDLE hThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)MyThread, NULL, 0, NULL);Sleep(3000);InitSecondModule();Sleep(3000);TerminateThread(hThread, 0);CloseHandle(hThread);return OK;
}int main(int argc, int *argv[]){TestFunPtr();getchar();return 0;
}
moduleAdmin.cpp
#include "moduleAdmin.h"#define MAX_PROC 100int g_iProCnt = 0; //全局的前面加一个g
MOUDLE_DATA_S FunList[MAX_PROC] = {0};int RegisterProc(int iModule, pProcFun pFun){if(g_iProCnt == MAX_PROC){return ERR;}FunList[g_iProCnt].iModule = iModule;FunList[g_iProCnt].pFun = pFun;g_iProCnt++;return OK;
}//调用注册的函数
int ExcuteAllModule(){for(int i = 0; i < g_iProCnt; i++){FunList[i].pFun();}return OK;
}
SecondModule.cpp
#include "SecondModule.h"int SecondModuleProc(){printf("Hello I am Second Module\n");return OK;
}int InitSecondModule(){RegisterProc(MY_READ_MODULE, SecondModuleProc);return OK;
}
源码打包
下载地址:
https://github.com/fengfanchen/CAndCPP/tree/master/CfunctionPtrAndCallBack
C语言工作笔记-对函数指针的进一步认识(与回调函数结合使用,并且对比C++的回调)相关推荐
- C++工作笔记-对二级指针的进一步理解(函数的参数使用二级指针,从而操作原数据)
二级指针不仅仅可以表示一个二维表(在邻接表里面用得比较多)! 当参数是一级指针的时候得到了是指向了同一个地址! 但参数是二级指针却有不同的效果! 如下代码: main.cpp #include< ...
- C++工作笔记-对二级指针的进一步理解(获取调用者的地址)
一般的项目中,如果要获取调用者参数的地址可以考虑使用二级指针. 程序运行截图如下: 源码如下: #include <iostream> #include <conio.h> u ...
- c++ 函数指针_进化论——从函数指针到被结构封装的函数指针及参数的应用举例...
↑↑↑ 点击上方公众号名称关注,不放过任何转变的机会. ✎ 编 者 悟 语 借口再小也会瓦解人的意志. 文 章 导 读 今天带大家用下函数指针,然后将函数指针和函数参数封装到结构体中,接着将数据用动态 ...
- 使用 typedef 定义函数指针,更优雅的使用函数指针
简介 关于函数指针的介绍,这里就不做过多说明了,不了解的同学可以看看这篇博客: https://blog.csdn.net/afei__/article/details/80549202 使用 typ ...
- 【C语言学习笔记】26. 指针(3)指向指针的指针、传递指针给函数
前言 指向指针的指针是一种多级间接寻址的形式,或者说是一个指针链.通常,一个指针包含一个变量的地址.当我们定义一个指向指针的指针时,第一个指针包含了第二个指针的地址,第二个指针指向包含实际值的位置. ...
- C++工作笔记-简单工厂模式基础(用静态类传入函数指针,再进行调用)(仿大佬代码)
代码如下: #include <iostream> using namespace std;typedef void(*LPFUNCTION)(int data); void regist ...
- C++_类和对象_对象特性_空指针访问成员函数_用法和问题解决---C++语言工作笔记050
然后我们再来看空指针访问成员函数,实际上在c++中null指针也是可以访问成员函数的, 有些人可能会觉得奇怪,不用奇怪. 去看看代码,去写个person类 写个showClassName()方法,打印 ...
- C++提高部分_C++函数模板_基本用法---C++语言工作笔记081
在c++中用到的主要技术,一个是面向对象,一个是 就是泛型编程,而泛型编程的主要实现技术就是利用模板技术实现的.可以看到c++提供了两种模板机制,一种是函数模板,一种是类模板, 我们这里先说,函数模板 ...
- C语言学习笔记----4(指针)
文章目录 指针深入介绍 指针类型 二级指针 字符指针 指针数组 数组指针 函数指针 函数指针数组 函数指针数组指针 回调函数 总结 指针深入介绍 众所周知,亚里士多德1撑起了古希腊科学.哲学的半壁江山 ...
最新文章
- 开发自己的山寨Android注解框架
- SQL Server不能启动
- 《UNIX环境高级编程(第3版)》——1.7 出错处理
- redis6.0中的多线程
- AC日记——斗地主(dfs)
- easy mysql_GitHub - aleafs/easymysql: mysql client in cluster, based on node-mysql
- Linux集群服务知识点总结及通过案例介绍如何实现高性能web服务(三)
- 【PKUWC2018】Minimax【线段树合并】
- 美团点评DBProxy读写分离使用说明
- Ubuntu 在终端下使用命令行打开pdf文件
- 区块链技术的发展现状_区块链的现状及其发展趋势
- SolarWinds 供应链攻击中的第四款恶意软件及其它动态
- python app逆向_python之app逆向破解data参数中的PassWord DES加密无填充
- sql server book
- Windows10安装ubuntu18.04双系统教程(双硬盘)
- 阿里一位 70 后程序员、架构师的 26 个职场感悟
- Android 版本4.12 微信,安卓4.12微信下载
- 【建站教程】网站引用三方图片遇到简单防盗链referer的处理办法
- 减法公式运算法则_数学加减法运算和运算法则
- CSGO地图制作常见问题