当前位置:   article > 正文

message_filters::Subscriber 的用法

message_filters::Subscriber 的用法

1.message_filters::Subscriber 是 ROS 中的消息订阅器类,用于接收和处理同步或异步消息。它提供了一种方便的方式来处理多个相关消息,并确保它们以相同的时间戳进行处理。

下面是message_filters::Subscriber 的详细用法:

(1)首先,你需要包含必要的头文件:
#include <ros/ros.h>
#include <message_filters/subscriber.h>

(2)创建一个ros::NodeHandle对象来与ROS系统通信:
ros::NodeHandle nh;

(3)创建一个ros::message_filters::Subscriber对象,并指定要订阅的话题和队列大小:
message_filters::Subscriber<MsgType> sub(nh, "topic_name", queue_size);
// 其中,MsgType是你想订阅的消息类型,例如std_msgs::String或自定义消息类型。

(4)设置回调函数来处理接收到的消息。你可以使用ros::MessageEvent<MsgType>作为回调函数参数类型,并在回调函数中访问消息内容,时间戳等信息:

void callback(const ros::MessageEvent<MsgType>& event)
{
    const MsgType::ConstPtr& msg = event.getConstMessage();
    ros::Time timestamp = event.getReceiptTime();
    // 处理消息
}


(5)创建一个ros::message_filters::Connection对象,将回调函数与订阅器对象连接起来:

message_filters::Connection conn = sub.registerCallback(callback);


(6)最后,调用ros::spin()函数开始接收和处理消息:

ros::spin();

或者使用ros::AsyncSpinner实现异步的消息处理:

ros::AsyncSpinner spinner(1);
spinner.start();
ros::waitForShutdown();

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36

这是 message_filters::Subscriber 的基本用法。通过使用消息过滤器,你可以轻松处理多个相关的消息,并确保它们以同步或异步的方式进行处理。你还可以组合不同的过滤器来满足更复杂的需求,例如时间同步等。请参考ROS文档中关于 message_filters 包的详细信息以了解更多高级用法和示例。

2.message_filters::Subscriberros::Subscriber 的区别

message_filters::Subscriberros::Subscriber 都是ROS中用于接收消息的订阅器类,但它们在功能和使用上有一些区别。

2.1 功能:

  • ros::Subscriber :是ROS的核心订阅器类,用于接收指定话题的消息。它提供了基本的消息订阅功能,可以接收任何类型的消息,并将其传递给回调函数进行处理。
  • message_filters::Subscriber:是 message_filters 库中的一个类,它基于 ros::Subscriber进行了封装和扩展,提供了更高级的消息过滤和同步功能。它可以同时接收多个相关的消息,并确保它们以相同的时间戳进行处理,或者通过其他条件进行消息过滤。

2.2使用方法:

  • ros::Subscriber:使用 ros::Subscriber时,你需要手动编写回调函数来处理接收到的消息,并使用ros::NodeHandle对象创建一个订阅器。你可以设置队列大小、消息过滤条件和回调函数等参数。
  • message_filters::Subscriber:与 ros::Subscriber 相比,使用message_filters::Subscriber时,你不需要手动编写回调函数,而是使用 ros::MessageEvent对象传递消息给回调函数。你还可以使用 message_filters::TimeSynchronizer 等其他过滤器来进行时间同步或其他类型的消息过滤。

综上所述,ros::Subscriber 是ROS中最基本的订阅器类,用于接收指定话题的消息。而 message_filters::Subscribermessage_filters 库提供的一个高级订阅器类,它在ros::Subscriber 的基础上提供了更复杂的消息过滤和同步功能。具体选择哪个类取决于你的需求:如果只需要基本的消息订阅功能,则可以使用 ros::Subscriber;如果需要处理多个相关消息或进行时间同步等高级功能,则可以使用 message_filters::Subscriber

3.例子
假设我们有两个话题,一个是机器人的位置信息(topic: “robot_position”),另一个是机器人的速度信息(topic: “robot_velocity”)。我们希望在接收到位置信息和速度信息时,打印它们的时间戳和内容。
3.1 使用 ros::Subscriber

#include <ros/ros.h>
#include <std_msgs/Float64.h>

void positionCallback(const std_msgs::Float64::ConstPtr& msg)
{
    ROS_INFO("Received position: [%f] at time: [%f]", msg->data, ros::Time::now().toSec());
}

void velocityCallback(const std_msgs::Float64::ConstPtr& msg)
{
    ROS_INFO("Received velocity: [%f] at time: [%f]", msg->data, ros::Time::now().toSec());
}

int main(int argc, char** argv)
{
    ros::init(argc, argv, "subscriber_example");
    ros::NodeHandle nh;
    
    ros::Subscriber pos_sub = nh.subscribe("robot_position", 10, positionCallback);
    ros::Subscriber vel_sub = nh.subscribe("robot_velocity", 10, velocityCallback);

    ros::spin();

    return 0;
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26

3.2使用 message_filters::Subscriber

#include <ros/ros.h>
#include <std_msgs/Float64.h>
#include <message_filters/subscriber.h>
#include <message_filters/time_synchronizer.h>

void callback(const std_msgs::Float64::ConstPtr& pos_msg, const std_msgs::Float64::ConstPtr& vel_msg)
{
    ROS_INFO("Received position: [%f] at time: [%f]", pos_msg->data, pos_msg->header.stamp.toSec());
    ROS_INFO("Received velocity: [%f] at time: [%f]", vel_msg->data, vel_msg->header.stamp.toSec());
}

int main(int argc, char** argv)
{
    ros::init(argc, argv, "message_filters_example");
    ros::NodeHandle nh;
    
    message_filters::Subscriber<std_msgs::Float64> pos_sub(nh, "robot_position", 10);
    message_filters::Subscriber<std_msgs::Float64> vel_sub(nh, "robot_velocity", 10);

    typedef message_filters::sync_policies::ApproximateTime<std_msgs::Float64, std_msgs::Float64> MySyncPolicy;
    message_filters::Synchronizer<MySyncPolicy> sync(MySyncPolicy(10), pos_sub, vel_sub);
    sync.registerCallback(boost::bind(&callback, _1, _2));

    ros::spin();

    return 0;
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28

在这两个例子中,我们分别使用了 ros::Subscribermessage_filters::Subscriber 来订阅两个不同的话题。通过回调函数,我们可以在接收到消息时打印出消息的时间戳和内容。

需要注意的是,第二个例子使用了 message_filters::TimeSynchronizer 来确保接收到的位置信息和速度信息具有相同的时间戳,以进行同步处理。你可以根据需要选择适当的消息过滤器策略(例如,ApproximateTime、ExactTime等)来控制同步的行为。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/盐析白兔/article/detail/813967
推荐阅读
相关标签
  

闽ICP备14008679号