回調函數

1、定義數組

什麼是回調函數?它首先是一個函數,這是確定的,我舉個例子:有兩個函數A和B,首先應用程序將A的地址告訴B,這稱之爲註冊回調函數,B在收到外部某個命令的時候,能夠根據B的地址來調用A,這個先被傳入B,後面又被B調用的函數A就稱之爲回調函數函數

這樣看來,判斷一個函數是否是回調函數是從它被調用的方式來定義的,那麼B函數通常來講須要一個傳入參數,參數類型是函數指針。spa

 

2、應用場景指針

有人可能會說,B想調用A直接在函數裏面直接調用就行了,爲何先要把A的地址做爲一個參數傳給B這麼麻煩呢?code

咱們能夠設想這樣一個生活場景:blog

商場裏有一款商品賣的特別好,常常賣斷貨,許多客戶都要求新貨一到就立刻聯繫他們,爲了商場能聯繫上客戶,客戶們就把本身的聯繫方式告訴商場(註冊回調函數),客戶A把本身的手機號告訴了商場,客戶B呢把本身的郵箱告訴了商場。等到新貨到了,商場就打電話(調用回調函數)通知客戶A,而通知客戶B則經過發郵件(調用回調函數)。接口

這裏咱們能夠看到,客戶把本身的聯繫方式告訴商場,至因而什麼聯繫方式商場並不關心,只要能聯繫上客戶就行,這樣就給客戶很大的靈活性。事件

再看一個具體的應用場景:回調函數

一個管理USB接口的模塊,這個模塊會不停的檢測USB接口是否有U盤插入。而當有U盤插入的這個事件發生時,不一樣的用戶可能想幹不一樣的事,好比有的用戶想在屏幕上顯示「有U盤插入了」,而有的用戶就想讓一個喇叭不停的響等等。那麼這個時候用戶只要把U盤插入響應函數的地址告訴模塊(註冊回調函數),等到模塊檢測到有U盤插入就去調用這個響應函數(調用回調函數),至於這個函數作些什麼,模塊並不關心,這就增長了用戶的靈活性,實現用戶想要的功能。event

 

3、怎麼用

 

從上面咱們看到須要把回調函數的地址做爲一個參數註冊到模塊中,這個函數地址其實就是個函數指針,既然要註冊到模塊中,這個回調函數必須以該模塊承認的格式編寫,說的比較抽象,下面舉個例子說明下。

先寫模塊部分,構造一個結構體

1 typedef struct _CheckEvent()
2 {
3  int eventID;
4  BOOL (*Check)(void);
5 }CheckEvent;

上面的結構體中定義了一個函數指針Check,參數是void,函數類型是BOOL,這就要求用戶定義的回調函數也必須是參數爲void、類型爲BOOL的函數。

接着定義一個CheckEvent的數組:

1 CheckEvent arrayCheckEvent[2]=
2 {
3   {0, CheckEvent0},//註冊回調函數CheckEvent0
4   {1, CheckEvent1}//註冊回調函數CheckEvent1
 };

編寫模塊主功能:

 1 void Module(void)
 2 {
int index,id;
3 while(1) 4 { 5 id=GetEventID();
7
for(index=0;index<2;index++) 8 { 9 if(id == arrayCheckEvent[index]. eventID)//當事件eventID發生時 10 arrayCheckEvent[index]. Check();//調用eventID對應的回調函數 11 } 12 } 13 }

應用程序要作的就是實現回調函數

BOOL CheckEvent0(void)和BOOL CheckEvent1(void)了,實現用戶想要的功能,注意回調函數的參數和函數類型要和模塊中定義的CheckEvent結構體中的函數指針定義的一致。

相關文章
相關標籤/搜索
本站公眾號
   歡迎關注本站公眾號,獲取更多信息