ROS通信架構(gòu)(下)

隊長與愛人相互七十年不能共舞,蟻人與女兒分隔五年未能相見,鋼鐵俠邂逅父親期盼新生,雷神遇見母親不忍分別。時間會給愛情設(shè)置衰老的考驗,給生命帶來變化的樂趣,會讓未盡千言凝成一個擁抱,讓遺憾萬般聚成一場話別。天神擁有肉身,超能淪為凡胎,你是一千四百萬分之一的勝利,是三千遍仍未盡的愛。——《復(fù)仇者聯(lián)盟4》

將繼續(xù)介紹ROS通信方式中的service、parameter server、actionlib。
Topic是ROS中的一種單向的異步通信方式。然而有些時候單向的通信滿足不了通信要求,比如當(dāng)一些節(jié)點(diǎn)只是臨時而非周期性的需要某些數(shù)據(jù),如果用topic通信方式時就會消耗大量不必要的系統(tǒng)資源,造成系統(tǒng)的低效率高功耗。

為了解決以上問題,service方式在通信模型上與topic做了區(qū)別。Service通信是雙向的,它不僅可以發(fā)送消息,同時還會有反饋。所以service包括兩部分,一部分是請求方(Clinet),另一部分是應(yīng)答方/服務(wù)提供方(Server)。這時請求方(Client)就會發(fā)送一request,要等待server處理,反饋回一個reply,這樣通過類似“請求-應(yīng)答”的機(jī)制完成整個服務(wù)通信。

這種通信方式的示意圖如下:
Node B是server(應(yīng)答方),提供了一個服務(wù)的接口,叫做 /Service ,我們一般都會用string類型來指定service的名稱,類似于topic。Node A向Node B發(fā)起了請求,經(jīng)過處理后得到了反饋。


Service是同步通信方式,所謂同步就是說,此時Node A發(fā)布請求后會在原地等待reply,直到Node B處理完了請求并且完成了reply,Node A才會繼續(xù)執(zhí)行。Node A等待過程中,是處于阻塞狀態(tài)的成通信。這樣的通信模型沒有頻繁的消息傳遞,沒有沖突與高系統(tǒng)資源的占用,
只有接受請求才執(zhí)行服務(wù),簡單而且高效。

Topic VS service
Srv

類似msg文件,srv文件是用來描述服務(wù)(service數(shù)據(jù)類型的,service通信的數(shù)據(jù)格式定義在*.srv中。它聲明了一個服務(wù),包括請求(request)和響應(yīng)(reply)兩部分。
舉例:
msgs_demo/srv/DetectHuman.srv

bool start_detect
---
my_pkg/HumanPose[] pose_data

msgs_demo/msg/HumanPose.msg,Srv只能嵌套msg,不能嵌套srv

std_msgs/Header header
string uuid
int32 number_of_joints
my_pkg/JointPose[]joint_data

msgs_demo/msg/JointPose.msg

string joint_name
geometry_msgs/Pose pose
floar32 confidence

以 DetectHUman.srv 文件為例,該服務(wù)例子取自O(shè)penNI的人體檢測ROS軟件包。它是用來查詢當(dāng)前深度攝像頭中的人體姿態(tài)和關(guān)節(jié)數(shù)的。srv文件格式很固定,第一行是請求的格式,中間用---隔開,第三行是應(yīng)答的格式。在本例中,請求為是否開始檢測,應(yīng)答為一個數(shù)組,數(shù)組的每個元素為某個人的姿(HumanPose)。而對于人的姿態(tài),其實(shí)是一個msg,所以srv可以嵌套msg在其中,但它不能嵌套srv。

修改部分文件

定義完了msg、srv文件,還有重要的一步就是修改package.xml和修改CMakeList.txt這些文件需要添加一些依賴:

<build_depend>** message_generation **</build_depend>
<run_depend>** message_runtime **</run_depend>

“**”所引就是新添加的依賴,又例如:

find_package(...roscpp rospy std_msgs ** message_generation **)
catkin_package(
...
CATJIN_DEPENDS ** message_runtime ** ...
...)
add_message_file(
FILES
** DetectHuman.srv **
** HumanPose.msg **
** JointPos.msg **)
** generate_messages(DEPENDENCIES std_msgs) **

添加的這些內(nèi)容指定了srv或者msg在編譯或者運(yùn)行中需要的依賴。具體的作用我們初學(xué)者可不深究,我們需要了解的是,無論我們自定義了srv,還是msg,修改上述部分添加依賴都是必不可少的一步。

Paramater server

介紹另外一種通信方式——參
數(shù)服務(wù)器(parameter server)。與前兩種通信方式不同,參數(shù)服務(wù)器也可以說是特殊的“通信方式”。特殊點(diǎn)在于參數(shù)服務(wù)器是節(jié)點(diǎn)存儲參數(shù)的地方、用于配置參數(shù),全局共享參數(shù)。參數(shù)服務(wù)器使用互聯(lián)網(wǎng)傳輸,在節(jié)點(diǎn)管理器中運(yùn)行,實(shí)現(xiàn)整個通信過程。

參數(shù)服務(wù)器,作為ROS中另外一種數(shù)據(jù)傳輸方式,有別于topic和service,它更加的靜態(tài)。參數(shù)服務(wù)器維護(hù)著一個數(shù)據(jù)字典,字典里存儲著各種參數(shù)和配置。

維護(hù)方式

參數(shù)服務(wù)器的維護(hù)方式非常的簡單靈活,總的來講有三種方式:

  • 命令行維護(hù)
  • launch文件內(nèi)讀寫
  • node源碼

Action

Actionlib是ROS中一個很重要的庫,類似service通信機(jī)制,actionlib也是一種請求響應(yīng)機(jī)制的通信方式,actionlib主要彌補(bǔ)了service通信的一個不足,就是當(dāng)機(jī)器人執(zhí)行一個長時間的任務(wù)時,假如利用service通信方式,那么publisher會很長時間接受不到反饋的reply,致使通信受阻。當(dāng)service通信不能很好的完成任務(wù)時候,actionlib則可以比較適合實(shí)現(xiàn)長時間的通信過程,actionlib通信過程可以隨時被查看過程進(jìn)度,也可以終止請求,這樣的一個特性,使得它在一些特別的機(jī)制中擁有很高的效率

Action規(guī)范

動作的內(nèi)容格式應(yīng)包含三個部分,目標(biāo)、反饋、結(jié)果。

  • 目標(biāo)
    機(jī)器人執(zhí)行一個動作,應(yīng)該有明確的移動目標(biāo)信息,包括一些參數(shù)的設(shè)定,方向、角度、速度等等。從而使機(jī)器人完成動作任務(wù)。
  • 反饋
    在動作進(jìn)行的過程中,應(yīng)該有實(shí)時的狀態(tài)信息反饋給服務(wù)器的實(shí)施者,告訴實(shí)施者動作完成的狀態(tài),可以使實(shí)施者作出準(zhǔn)確的判斷去修正命令。
  • 結(jié)果
    當(dāng)運(yùn)動完成時,動作服務(wù)器把本次運(yùn)動的結(jié)果數(shù)據(jù)發(fā)送給客戶端,使客戶端得到本次動作的全部信息,例如可能包含機(jī)器人的運(yùn)動時長,最終姿勢等等。
    Action規(guī)范文件的后綴名是.action,它的內(nèi)容格式如下:
# Define the goal
uint32 dishwasher_id # Specify which dishwasher we want to use
---
# Define the result
uint32 total_dishes_cleaned
---
# Define a feedback message
float32 percent_complete
Action實(shí)例詳解

Actionlib是一個用來實(shí)現(xiàn)action的一個功能包集。我們在demo中設(shè)置一個場景,執(zhí)行一個搬運(yùn)的action,搬運(yùn)過程中客戶端會不斷的發(fā)回反饋信息,最終完成整個搬運(yùn)過程。
首先寫handling.action文件,類比如上的格式.包括三個部分,目標(biāo),結(jié)果,反饋.如下:

# Define the goal
uint32 handling_id
---
# Define the result
uint32 Handling_completed
---
# Define a feedback message
float32 percent_complete

寫完之后修改文件夾里CmakeLists.txt如下內(nèi)容:

1. find_package(catkin REQUIRED genmsg actionlib_msgs actionlib)
2. add_action_files(DIRECTORY action FILES DoDishes.action)
generate_messages(DEPENDENCIES actionlib_msgs)
3. add_action_files(DIRECTORY action FILES Handling.action)
4. generate_messages( DEPENDENCIES actionlib_msgs)

修改package.xml,添加所需要的依賴如下:

1. <build_depend>actionlib </build_depend>
2. <build_depend>actionlib_msgs</build_depend>
3. <run_depend>actionlib</run_depend>
4. <run_depend>actionlib_msgs</run_depend>

然后回到工作空間 catkin_ws 進(jìn)行編譯:
定義了一個搬運(yùn)的例子,首先寫客戶端,實(shí)現(xiàn)功能發(fā)送action請求,包括進(jìn)行目標(biāo)活動,或者目標(biāo)活動.之后寫服務(wù)器,實(shí)驗返回客戶端活動當(dāng)前狀態(tài)信息,結(jié)果信息,和反饋信息.從而實(shí)現(xiàn)action.

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容