1. 程式人生 > >c++回撥函式/ROS回撥函式

c++回撥函式/ROS回撥函式

以下均是個人在實際耕碼的過程中遇到的問題和整理的結果,可能會有不對的地方,望各位指正與交流

------------------------------------------------------------------我會有喵的-------------------------------------------------------------------

c++中的回撥函式:

A "callback" is any function that is called by another function which takes the first function as a parameter.

直白點說,就是“函式#"的引數是另一個函式,通過“函式#"呼叫另一個函式,這個“函式#"就是回撥函式。以數學形式來看(雖然不太恰當):Function(y)和Function(g(x))。Function(y)是一個函式,g(x)也是一個函式,那麼Function(g(x))就可以看成是一個回撥過程,g(x)就是回撥函式。

更直接地說,我們一般都是呼叫opencv裡面的庫函式,現在關係反過來了,我們要讓opencv呼叫一個我們自己寫的函式,這個過程就是回撥。那個被opencv呼叫的(我們自己寫的)函式就是回撥函式。接下來舉例規範地說一下:

不帶引數的回撥函式:

//回撥函式
void wordsCallback() 
{
   std::cout<<"Hello World!"<<std::endl;
}

//實現回撥函式的"呼叫函式"
void wods(void (*callfuction)())
{
    callfuction();
}

int main(int argc,char* argv[])
{
    words(wodsCallback);
    return 0;
} 

 程式的正確輸出結果是:Hello World!

  帶引數的回撥函式:

//回撥函式
void wordsCallback(char* s) 
{   
   std::cout<<s<<std::endl;
}

//實現帶參回撥函式的"呼叫函式"
void words(void (*callfuction)(char*),char* s)
{
    callfuction(s);
}

int main(int argc,char* argv[])
{
    words(wordsCallback,"Hello World!");
    return 0;
}

程式的正確輸出結果:Hello World!

接下來我們看看ROS中的回撥函式。一般來說這個回撥函式會用一些比較顯著且比較統一的名字:**Callback(如ScanCallback/CameraCallback),它是在訂閱話題的時候使用的。所以在使用時,我們需要宣告訂閱話題的名稱,然後選擇話題,最後呼叫Callback函式。廢話不多說,舉個例子(突然想吃舉個栗子了啊-------):

ros::Subscriber sub_raw_image = n.subscribe(IMAGE_TOPIC, 2000, imageCallback);
先宣告訂閱的話題的名稱:
sub_raw_image 

然後,選擇我們需要訂閱的話題。

IMAGE_TOPIC
題外話,ROS中有很多話題,你可以自己寫,上面這個IMAGE_TOIC就是我自己寫的。當然你也可以使用一些系統提供的。比如你啟動了鐳射雷達,不論是模擬Gazebo中的還是真的鐳射雷達(如rplidar),那你就可以訂閱“/scan”這個話題。

2000代表我們一次性可以快取多少訊息(暫時沒發現這個數字對我的程式會帶來很大的影響,我經常寫成1),最後那個就是回撥函數了。

imageCallback
對於imageCallback的實現需要說一下。ROS中,imageCallback的引數是與你的話題息息相關的,你要跟據訂閱的話題來確定引數。一般來說,程式的主要功能也都是在回撥函式中實現的。你需要的資料,都是要通過話題訂閱的,而訂閱了就肯定有回撥函式。你可以把一個個回撥函式看成是一個個單獨的執行緒。只要你訂閱的訊息一更新,回撥函式就會被呼叫,對新的資料進行處理,程式就這麼不斷的進行下去了。這裡我們仍舊舉例:
void forwardCallback(const nav_msgs::Odometry::ConstPtr &forward_msg){}

void imageCallback(const sensor_msgs::ImageConstPtr &image_msg){}

需要確定的就是這個sensor_msgs::ImageConstPtr和nav_msgs::Odometry::ConstPtr啦!

嗯啊,今天到此結束啦,白白!