函數調用很好理解,即使剛學沒多久的朋友也知道函數調用是怎么實現的,即調用一個已經封裝好的函數,實現某個特定的功能。
把一個或者多個功能通過函數的方式封裝起來,對外只提供一個簡單的函數接口,然后在其他地方調用即可
函數調用方式函數調用難道還能怎么調用?不就封裝好直接調用嗎???
函數調用方式分為兩種:直接調用和間接調用
直接調用
直接調用就是我們平常使用的方式,下面的方式就屬于直接調用了。
intSumFun(inta,intb)
{
returna+b;
}
intmain()
{
//直接調用定義好的函數
intsum=SumFun(5,6);
printf("sum=%d",sum);
return0;
}
間接調用
間接調用在初學時很難使用到,這是通過函數指針的方式實現的。
函數指針本質是一個指針變量,是一個指向函數的指針(函數本身也是有地址的,指向的是函數入口);
而指針函數本質是一個函數,其返回值為指針。
函數指針的用法如下:
typedefint(*FunctionCB)(int,int);
intSumFun(inta,intb)
{
returna+b;
}
intmain()
{
//將定義好的函數賦值給函數指針
FunctionCBpfnSum=SumFun;
//通過函數指針間接調用
intsum=pfnSum(5,6);
printf("sum=%d",sum);
return0;
}
什么場景使用
函數指針在軟件架構分層設計中十分重要,因為分層設計中有一個設計原則,那就是下層函數不能直接調用上層函數,那么可以通過函數指針的方式實現;一般稱上層通過函數指針賦值給下層的函數為回調函數。
什么情況會存在需要下層程序需要調用上層程序的呢?
比如串口數據接收,雖然可以通過查詢的方式接收,但是遠不及通過串口中斷的方式接收及時,當接收完成時,需要立即通知上層讀取數據進行處理,而不是等待上層程序查詢讀取。
如何實現呢?
比如硬件抽象層/驅動層中的串口模塊實現函數
/*************UART.c文件****************/
staticUartRecvCBsg_pfnUartRecv;
//設置數據幀接收處理回調函數
voidUART_SetRecvCallback(UartRecvCBpfnUartRecv)
{
sg_pfnUartRecv=pfnUartRecv;
}
voidUART_Task(void)
{
if(RecvEnd)
{
//數據一幀接收完成立即調用
if(sg_pfnUartRecv!=NULL)
{
sg_pfnUartRecv(UartRecvBuf,UartRecvLength);
}
}
}
/*************UART.h文件****************/
typedefvoid(*UartRecvCB)(constchar*,int);
externvoidUART_SetRecvCallback(UartRecvCBpfnUartRecv);
externvoidUART_Task(void);
應用層代碼中實現回調函數,并調用下層函數。
//回調函數:串口數據處理
voidOnUartRecvProcess(constchar*pBuf,intlength)
{
//處理串口數據
printf("Recv:%s",pBuf);
}
intmain()
{
UART_SetRecvCallback(OnUartRecvProcess);
while(1)
{
if(TimeFlag)
{
UART_Task();
}
}
}
上述示例中通過函數指針的方式間接調用了應用層的函數,而且并不違背分層設計原則。
如果看代碼不能立即理解的話,可以嘗試通過下圖理解:
-
嵌入式
+關注
關注
5087文章
19153瀏覽量
306425 -
接口
+關注
關注
33文章
8667瀏覽量
151524
原文標題:函數調用在嵌入式架構設計中的應用
文章出處:【微信號:strongerHuang,微信公眾號:strongerHuang】歡迎添加關注!文章轉載請注明出處。
發布評論請先 登錄
相關推薦
評論