ROS学习(基于Ubuntu 15.04 和ROS Jade)第三章 ROS核心教程 之 13 编写简单的服务器和客户端

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/jrc_january/article/details/76576112

引言

本节介绍如何编写服务器和客户端节点。

1.编写service节点

我们将创建一个简单的service节点(add_two_ints_server),该节点接收两个整形数字并返回它们的和。要确保已经安装之前的教程创建了所需要的srv。
在beginner_tutorials/src目录中创建add_two_ints_server.cpp文件

1.1 源代码

#include "ros/ros.h"
#include "beginner_tutorials/AddTwoInts.h"

bool add(beginner_tutorials::AddTwoInts::Request  &req,
         beginner_tutorials::AddTwoInts::Response &res)
{
  res.sum = req.a + req.b;
  ROS_INFO("request: x=%ld, y=%ld", (long int)req.a, (long int)req.b);
  ROS_INFO("sending back response: [%ld]", (long int)res.sum);
  return true;
}

int main(int argc, char **argv)
{
  ros::init(argc, argv, "add_two_ints_server");
  ros::NodeHandle n;

  ros::ServiceServer service = n.advertiseService("add_two_ints", add);
  ROS_INFO("Ready to add two ints.");
  ros::spin();

  return 0;
}

1.2 explained

#include "beginner_tutorials/AddTwoInts.h"

beginner_tutorials/AddTwoInts.h是之前由编译器根据我们创建的srv文件生成的头文件。


bool add(beginner_tutorials::AddTwoInts::Request  &req,beginner_tutorials::AddTwoInts::Response &res)
{
  res.sum = req.a + req.b;

  ROS_INFO("request: x=%ld, y=%ld", (long int)req.a, (long int)req.b);

  ROS_INFO("sending back response: [%ld]", (long int)res.sum);

  return true;
}

这是一个请求回调函数,当请求到达时,执行此函数。
- 两个参数一个是请求的数据req,另一个是应当的数据res。
- 该函数将请求数据的两个成员相加并装入应答数据。
- 打印了一些消息,用于记录。
- 最后任务完成返回true。


ros::ServiceServer service = n.advertiseService("add_two_ints", add);

nodehandle::advertiseService()用于告知master 该节点提供了什么样的服务,服务名为第一个参数,第二个参数为收到服务请求后的处理函数。

2. 编写Client节点

在src/目录中创建add_two_ints_client.cpp文件。

2.1 源码

#include "ros/ros.h"
#include "beginner_tutorials/AddTwoInts.h"
#include <cstdlib>

int main(int argc, char **argv)
{
  ros::init(argc, argv, "add_two_ints_client");
  if (argc != 3)
  {
    ROS_INFO("usage: add_two_ints_client X Y");
    return 1;
  }

  ros::NodeHandle n;
  ros::ServiceClient client = n.serviceClient<beginner_tutorials::AddTwoInts>("add_two_ints");
  beginner_tutorials::AddTwoInts srv;
  srv.request.a = atoll(argv[1]);
  srv.request.b = atoll(argv[2]);
  if (client.call(srv))
  {
    ROS_INFO("Sum: %ld", (long int)srv.response.sum);
  }
  else
  {
    ROS_ERROR("Failed to call service add_two_ints");
    return 1;
  }

  return 0;
}

2.2 源码解释

 if (argc != 3)
  {
    ROS_INFO("usage: add_two_ints_client X Y");
    return 1;
  }

这里检查了传入的参数。节点名和两个被求和值。因为用的了ROS_INFO()函数,所以在此之前先要执行ros::init().


ros::ServiceClient client = n.serviceClient<beginner_tutorials::AddTwoInts>("add_two_ints");

这里使用nodehandle::serviceClient<>()成员函数创建了一个ROS客户端,接下来将使用该客户端调用ROS 服务。


  beginner_tutorials::AddTwoInts srv;
  srv.request.a = atoll(argv[1]);
  srv.request.b = atoll(argv[2]);

这里实例化了一个服务,并给其请求成员赋值。


 if (client.call(srv))

这里调用了服务。
service的调用时阻塞的,调用成功返回true,此时response的值是有效的。若调用失败则返回false,此时response的值是无效的。

3. 编译

3.1 修改CMakeLists.txt文件

修改beginner_tutorials中的CMakeLists.txt,添加以下内容:

add_executable(add_two_ints_server src/add_two_ints_server.cpp)
target_link_libraries(add_two_ints_server ${catkin_LIBRARIES})
add_dependencies(add_two_ints_server beginner_tutorials_gencpp)

add_executable(add_two_ints_client src/add_two_ints_client.cpp)
target_link_libraries(add_two_ints_client ${catkin_LIBRARIES})
add_dependencies(add_two_ints_client beginner_tutorials_gencpp)

CMakeLists.txt文件的编写参考以下:

http://wiki.ros.org/catkin/CMakeLists.txt

3.2 执行编译

在catkin workspace下执行catkin_make命令:

$ cd ~/catkin_ws
$ catkin_make

这将在devel space目录下生成两个可执行程序 “add_two_ints_server”和“add_two_ints_client”,执行后分别是服务器节点和客户端节点。

猜你喜欢

转载自blog.csdn.net/jrc_january/article/details/76576112