[ROS2] 动手实践Costmap新特性

Cartographer ROS Integration Cartographer ROS Integration一、Configuration配置二、调试2.1 两个系统2.2 局部SLAM2.3 验证三、ROS API3.1 Cartographer 节点3.2 离线节点3.3 占据栅格节点四、包含的资源?(Assets writer)4.1 采样指南4.2 配置4.3 点云的第一人称视角的可视化五、demos5.1 仅局部的5.2 Revo LDS... 阅读详情

废话不多说,我们直接开始。

搭建测试环境

为了避免花太多时间折腾环境问题。这里使用Docker来跑测试的示例。

安装Docker

# step 1: 安装必要的一些系统工具
sudo apt-get update
sudo apt-get -y install apt-transport-https ca-certificates curl software-properties-common

# step 2: 安装GPG证书
curl -fsSL http://mirrors.aliyun.com/docker-ce/linux/ubuntu/gpg | sudo apt-key add -

# Step 3: 写入软件源信息
sudo add-apt-repository "deb [arch=amd64] http://mirrors.aliyun.com/docker-ce/linux/ubuntu $(lsb_release -cs) stable"

# Step 4: 更新并安装 Docker-CE
sudo apt-get -y update
sudo apt-get -y install docker-ce

# Step 5: 查看docker是否安装成功
docker version

也可以使用小鱼提供的开源一键安装工具。关注小鱼的公众号《鱼香ROS》获取更多信息。

工具网址: https://fishros.com/docs/page/#/tools/install-ros/%E4%B8%80%E8%A1%8C%E4%BB%A3%E7%A0%81%E5%AE%89%E8%A3%85%E5%AE%8C%E6%88%90ROS

wget http://fishros.com/install -O fishros && . fishros

该命令需要在bash命令窗口运行,zsh命令窗口运行会出错。请知晓。

拉取Docker镜像

docker pull shoufei/ros2_galactic:latest_v_0_1

拉取示例代码

git clone https://gitee.com/shoufei/ros2_galactic.git

启动Docker环境

注意:下面命令中的/path_to/ros2_galactic需要改成你自己的路径

docker run -it \
-v /etc/localtime:/etc/localtime:ro \
-v /tmp/.X11-unix:/tmp/.X11-unix \
-v /path_to/ros2_galactic:/home/ubuntu/ros2_galactic \
-e DISPLAY=unix$DISPLAY \
-e GDK_SCALE \
-e GCK_DPI_SCALE \
-p 6080:80 \
--device /dev/snd \
--name ros2_desktop_galactic_latest \
--privileged \
--security-opt seccomp:unconfined \
--security-opt apparmor:unconfined \
shoufei/ros2_galactic:latest_v_0_1 /bin/bash

打开多个Docker环境的命令窗口

先查询docker的id。每台电脑上的id是随机生成的,请以自己的id为准。

docker ps -a

找到对应的CONTAINER ID。

使用下面的命令登录Docker容器

docker exec -it 31ced27e1684 /bin/bash  #31ced27e1684是容器的id

切换容器中的用户名为ubuntu(这句要进入到容器中才执行)

su ubuntu

如果对Docker不是很了解,可以关注公众号《首飞》,回复”docker“。可以收到一本关于docker的电子书。希望能帮你入门。

启动测试命令

启动仿真环境

ros2 launch turtlebot3_gazebo turtlebot3_world.launch.py 

如果想测试KeepoutFilter就启动KeepoutFilter对应的命令,若想测试SpeedFilter就启动SpeedFilter对应的命令,不需要两个都启动。仿真环境和NAV2 Stack在更换测试内容时要重新启动。每个命令需要在不同的命令窗口中启动,所以要开启三个Docker环境的命令窗口。

测试KeepoutFilter

制作Keepout Mask

在navigation2_tutorials/nav2_costmap_filters_demo/maps目录下,重新拷贝一份map.pgm和map.yaml并重命名文件。

需要注意的是,yaml文件中的image: map.pgm参数需要改成重新命名的名字。

可以通过下面的命令打开图片并且编辑。

gimp keepout_dark_mask.pgm

注:keepout_dark_mask为示例图片的名称,你需要改成自己的。

系统中没有安装gimp的话,按照下面的方法安装:

sudo apt update
sudo add-apt-repository ppa:otto-kesselgulasch/gimp
sudo apt install gimp

当然也可以使用其他自己比较熟悉的图片编辑器。

编辑操作方法查看下面的视频:

[ROS2] 制作costmap keepout mask

启动nav2_costmap_filters_demo节点

启动keepout相关NAV2 Stack

ros2 launch turtlebot3_navigation2 navigation2_keepout.launch.py use_sim_time:=True

运行下面的命令加载KeepoutFilter:

下面有三个不同颜色深浅的keepout区域示例。可以分别启动试试效果。

注意:需要在工程包的src目录的上级目录运行下面的命令。

ros2 launch nav2_costmap_filters_demo costmap_filter_info.launch.py params_file:=src/navigation2_tutorials/nav2_costmap_filters_demo/params/keepout_params.yaml mask:=src/navigation2_tutorials/nav2_costmap_filters_demo/maps/keepout_mask.yaml
ros2 launch nav2_costmap_filters_demo costmap_filter_info.launch.py params_file:=src/navigation2_tutorials/nav2_costmap_filters_demo/params/keepout_params.yaml mask:=src/navigation2_tutorials/nav2_costmap_filters_demo/maps/keepout_light_mask.yaml
ros2 launch nav2_costmap_filters_demo costmap_filter_info.launch.py params_file:=src/navigation2_tutorials/nav2_costmap_filters_demo/params/keepout_params.yaml mask:=src/navigation2_tutorials/nav2_costmap_filters_demo/maps/keepout_dark_mask.yaml

如果你自行绘制了mask图片,则需将mask的地址更改一下。

这里有一个细节需要关注。

filters放在了plugins后面才被添加到combined_costmap_。这样的话,KeepoutFilter中人为标记的障碍物将不会被膨胀。

    // Costmap Filters enabled
    // 1. Update costmap by plugins
    primary_costmap_.resetMap(x0, y0, xn, yn);
    for (vector<std::shared_ptr<Layer>>::iterator plugin = plugins_.begin();
      plugin != plugins_.end(); ++plugin)
    {
      (*plugin)->updateCosts(primary_costmap_, x0, y0, xn, yn);
    }

    // 2. Copy processed costmap window to a final costmap.
    // primary_costmap_ remain to be untouched for further usage by plugins.
    if (!combined_costmap_.copyWindow(primary_costmap_, x0, y0, xn, yn, x0, y0)) {
      RCLCPP_ERROR(
        rclcpp::get_logger("nav2_costmap_2d"),
        "Can not copy costmap (%i,%i)..(%i,%i) window",
        x0, y0, xn, yn);
      throw std::runtime_error{"Can not copy costmap"};
    }

    // 3. Apply filters over the plugins in order to make filters' work
    // not being considered by plugins on next updateMap() calls
    for (vector<std::shared_ptr<Layer>>::iterator filter = filters_.begin();
      filter != filters_.end(); ++filter)
    {
      (*filter)->updateCosts(combined_costmap_, x0, y0, xn, yn);
    }

primary_costmap_主要用于合并所有plugins_的栅格值。然后combined_costmap_再合并primary_costmap_和所有filters。这样的处理是防止plugins和filters之间互相干扰。

对于keepout_filter,通常需要在global_costmap和local_costmap中都需要配置keepout_filter。这样的话,这两个层都能感知到虚拟墙。

keepout_filter的配置方式如下:

filters: ["keepout_filter"]
keepout_filter:
    plugin: "nav2_costmap_2d::KeepoutFilter"
    enabled: True
    filter_info_topic: "/costmap_filter_info"

效果如下:

[ROS2] costmap keepout demo no inflation

当keepout_filter按照如下方式配置时,我们可以看到虚拟障碍物的膨胀效果:

plugins: ["obstacle_layer", "voxel_layer", "keepout_filter", "inflation_layer"]
keepout_filter:
    plugin: "nav2_costmap_2d::KeepoutFilter"
    enabled: True
    filter_info_topic: "/costmap_filter_info"

注意:keepout_filter被放置在了plugins标签下,并且在inflation_layer之前。

[ROS2] keepout demo inflation

测试SpeedFilter

制作Speed Mask

Speed Mask的制作方法和Keepout Mask是一样的。但是mask加载的模式会有区别。

Speed Mask的配置文件(navigation2_tutorials/nav2_costmap_filters_demo/maps/speed_mask.yaml)如下:

image: speed_mask.pgm
mode: scale
resolution: 0.050000
origin: [-10.000000, -10.000000, 0.000000]
negate: 0
occupied_thresh: 1.0
free_thresh: 0.0

其中mode设置为scale。free_thresh = 0.0 和 occupied_thresh = 1.0表示以1:1的方式映射亮度值到速度限制百分比。

启动Speedlimit相关NAV2 Stack

ros2 launch turtlebot3_navigation2 navigation2_speedlimit.launch.py use_sim_time:=True

启动nav2_costmap_filters_demo节点

运行下面的命令加载SpeedFilter:

ros2 launch nav2_costmap_filters_demo costmap_filter_info.launch.py params_file:=src/navigation2_tutorials/nav2_costmap_filters_demo/params/speed_params.yaml mask:=src/navigation2_tutorials/nav2_costmap_filters_demo/maps/speed_mask.yaml
ros2 launch nav2_costmap_filters_demo costmap_filter_info.launch.py params_file:=src/navigation2_tutorials/nav2_costmap_filters_demo/params/speed_params.yaml mask:=src/navigation2_tutorials/nav2_costmap_filters_demo/maps/speed_light_mask.yaml

这里同样有一个细节需要注意。

SpeedFilter只需要在global_costmap中进行配置,不需要在local_costmap中配置。因为这个filter主要的作用是根据机器人是否在设定的区域来限制机器人的速度。而设定的区域的栅格值并不会更新到combined_costmap_中。这一点查看该filter的处理函数就很清楚了。

void SpeedFilter::process(
  nav2_costmap_2d::Costmap2D & /*master_grid*/,
  int /*min_i*/, int /*min_j*/, int /*max_i*/, int /*max_j*/,
  const geometry_msgs::msg::Pose2D & pose)
{
  std::lock_guard<CostmapFilter::mutex_t> guard(*getMutex());

  if (!filter_mask_) {
    // Show warning message every 2 seconds to not litter an output
    RCLCPP_WARN_THROTTLE(
      logger_, *(clock_), 2000,
      "SpeedFilter: Filter mask was not received");
    return;
  }

  geometry_msgs::msg::Pose2D mask_pose;  // robot coordinates in mask frame

  // Transforming robot pose from current layer frame to mask frame
  if (!transformPose(pose, mask_pose)) {
    return;
  }

  // Converting mask_pose robot position to filter_mask_ indexes (mask_robot_i, mask_robot_j)
  unsigned int mask_robot_i, mask_robot_j;
  if (!worldToMask(mask_pose.x, mask_pose.y, mask_robot_i, mask_robot_j)) {
    return;
  }

  // Getting filter_mask data from cell where the robot placed and
  // calculating speed limit value
  int8_t speed_mask_data = getMaskData(mask_robot_i, mask_robot_j);
  if (speed_mask_data == SPEED_MASK_NO_LIMIT) {
    // Corresponding filter mask cell is free.
    // Setting no speed limit there.
    speed_limit_ = NO_SPEED_LIMIT;
  } else if (speed_mask_data == SPEED_MASK_UNKNOWN) {
    // Corresponding filter mask cell is unknown.
    // Do nothing.
    RCLCPP_ERROR(
      logger_,
      "SpeedFilter: Found unknown cell in filter_mask[%i, %i], "
      "which is invalid for this kind of filter",
      mask_robot_i, mask_robot_j);
    return;
  } else {
    // Normal case: speed_mask_data in range of [1..100]
    speed_limit_ = speed_mask_data * multiplier_ + base_;
    if (percentage_) {
      if (speed_limit_ < 0.0 || speed_limit_ > 100.0) {
        RCLCPP_WARN(
          logger_,
          "SpeedFilter: Speed limit in filter_mask[%i, %i] is %f%%, "
          "out of bounds of [0, 100]. Setting it to no-limit value.",
          mask_robot_i, mask_robot_j, speed_limit_);
        speed_limit_ = NO_SPEED_LIMIT;
      }
    } else {
      if (speed_limit_ < 0.0) {
        RCLCPP_WARN(
          logger_,
          "SpeedFilter: Speed limit in filter_mask[%i, %i] is less than 0 m/s, "
          "which can not be true. Setting it to no-limit value.",
          mask_robot_i, mask_robot_j);
        speed_limit_ = NO_SPEED_LIMIT;
      }
    }
  }

  if (speed_limit_ != speed_limit_prev_) {
    if (speed_limit_ != NO_SPEED_LIMIT) {
      RCLCPP_DEBUG(logger_, "SpeedFilter: Speed limit is set to %f", speed_limit_);
    } else {
      RCLCPP_DEBUG(logger_, "SpeedFilter: Speed limit is set to its default value");
    }

    // Forming and publishing new SpeedLimit message
    std::unique_ptr<nav2_msgs::msg::SpeedLimit> msg =
      std::make_unique<nav2_msgs::msg::SpeedLimit>();
    msg->header.frame_id = global_frame_;
    msg->header.stamp = clock_->now();
    msg->percentage = percentage_;
    msg->speed_limit = speed_limit_;
    speed_limit_pub_->publish(std::move(msg));

    speed_limit_prev_ = speed_limit_;
  }
}

在global_costmap中的配置如下:

filters: ["speed_filter"]
speed_filter:
    plugin: "nav2_costmap_2d::SpeedFilter"
    enabled: True
    filter_info_topic: "/costmap_filter_info"
    speed_limit_topic: "/speed_limit"

速度限制的方式有两种:

  • 限制为最大速度的多少百分比
  • 限制绝对最大速度

在这个实践示例中采用第一种以百分比限制速度的方式。该方式的配置在navigation2_tutorials/nav2_costmap_filters_demo/params/speed_params.yaml文件中。参数内容如下:

costmap_filter_info_server:
  ros__parameters:
    use_sim_time: true
    type: 1
    filter_info_topic: "/costmap_filter_info"
    mask_topic: "/speed_filter_mask"
    base: 100.0
    multiplier: -1.0
filter_mask_server:
  ros__parameters:
    use_sim_time: true
    frame_id: "map"
    topic_name: "/speed_filter_mask"
    yaml_filename: "speed_mask.yaml"

其中type为1表示采用百分比限制速度的方式。base设置为100,multiplier设置为-1.0是对应type来设置的。

速度限制的计算公式:

// Normal case: speed_mask_data in range of [1..100]
speed_limit_ = speed_mask_data * multiplier_ + base_;

speed_mask_data为OccupancyGrid中的栅格值,范围为0~100。根据上面的计算公式,将产生这样的效果:颜色越深,栅格值speed_mask_data越大,最后得到的speed_limit_(速度限制百分比)越小。

如果我们只想让速度限制百分比在一个区间中变动,比如[40.0%..50.0%]。可以这样base = 40.0, multiplier = 0.1设置。速度限制百分比将以0.1%的步长在[40.0%..50.0%]区间内变动。

当speed_limit_为0的时候表示没有速度限制,所以当画的mask区域颜色非常深,是障碍物的深度,可能计算出来的速度限制百分比为0。

速度限制效果如下:

[ROS2] costmap speed

实践参考

Navigating with Keepout Zones

Navigating with Speed Limits

更多关于costmap,keepout_filter和speed_filter的详细内容请查看之前发布文章:

Navigation:costmap是什么?

[ROS2] 你应该知道Costmap_2d 的这些细节


文章在公众号《首飞》中首发,因为各平台视频链接不兼容的关系,部分视频没有加入到文章中。公众号的文章中有更多的演示视频来帮助大家理解。

最近在写ROS2相关的文章,如果你有感兴趣的话题,希望我来写一写,可以与我交流。个人微信可以在公众号《首飞》里找到。谢谢!

ROS2 Navigation2中的代价地图 (Costmap) 详解 代价地图 (Costmap) 是ROS2 Navigation2中一个至关重要的概念。它本质上是一个二维或三维的栅格地图,其中的每个栅格(cell)都被赋予一个“代价值”(cost value),用以表示机器人移动到该位置的成本或风险。 阅读详情

相关推荐

ROS naviagtion analysis: costmap_2d--Costmap2DROS

在上一篇文章中moveBase就有关于costmap_2d的使用: planner_costmap_ros_是用于全局导航的地图,controller_costmap_ros_是局部导航用的地图,地图类型为经过ROS封装的costmap_2d::Costmap2DROS*。 以下是这个ROS类的UML: 看看这个类的成员变量:LayeredCostmap* layered_costmap_

BjtRob的专栏 7340

[ROS2] map_server加载地图文件的三种模式

map的数据类型 map话题的类型是nav_msgs::msg::OccupancyGrid。使用下面的命令可以查询该类型的数据结构。 ros2 interface show nav_msgs/msg/OccupancyGrid nav_msgs::msg::OccupancyGrid的数据结构: # This represents a 2-D grid map std_msgs/Header header builtin_interfaces/Time stamp

首飞的博客 3672

ROS 进阶学习笔记(16):ROS导航1:关于Costmap_2d Package (代价地图包)

=== 关于Costmap_2d Package === wiki page: http://wiki.ros.org/costmap_2d === 我学这个包的时候,尽量总结wiki page上的内容如下:=== 所属Stack: navigation Sammary:    1. 实现2D cost map    2. 输入: sensor data    3. 生成:

Combine Art and Sciences. 1万+

ROS基础教程--CostMap_2D包的一些理解

本文是在综合了多篇文章的基础之上进行的综合.1.基本概念 Voxel:体素,即顾名思义是体积的像素。用来在三维空间中表示一个显示基本点的单位。类似于二维平面下的pixel(像素)。voxel是三维空间中定义一个点的图象信息的单位。在平面中定义一个点要两个坐标X和Y就够了,而在三维世界中还要有一个坐标。光有3维坐标位置还不行,还要有颜色等信息,这就是voxel的含义。机器人在costmap_2D中的...

jinking01的专栏 2万+

ROS导航系列(三):costmap2D详解

功能包costmap2D提供一种

miya的博客 6481

ROS naviagtion analysis: costmap_2d--Costmap2D

Costmap2D是存储地图数据的父类。真正的地图数据就存储在数据成员unsigned char *costmap_ 。 首先,分析类的构造函数: 默认构造函数:Costmap2D::Costmap2D() :// just initialize everything to NULL by default Costmap2D::Costmap2D() : size_x_(0), siz

BjtRob的专栏 2984

ROS Melodic中costmap2D详解

0 概述 如果需要深入了解navigation,那costmap2D必不可少。本文章参考了多篇文章以及ros navigation官网最新的资料,并结合自身的理解完成。该软件作为栅格地图建立的函数包,其输入是现实传感器的数据,输出是2D栅格地图的costmap,该软件包还支持基于map_server的costmap初始化(调用map_server节点,以服务的方式读取地图数据),基于滚动窗口的costmap初始化,以及基于参数的订阅和传感器主题的配置。 1 cost值 可以这么说,无论是激光雷达还是如kin

lovely_yoshino的博客 8634

【ROS】Nav2源码之nav2_costmap_2d(代价地图)详解

Costmap2DROS是 2D Costmap 的ROS封装,可以订阅以PointCloud或LaserScan为消息形式的主题,用以观察障碍物。Costmap2DROS也是从 node_interfaces::LifecycleNodeInterface继承而来,都是通过状态机来实现生命周期管理。

郭老二 2195

ros-navigation学习笔记(四)costmap代价地图

0x00 什么是costmap代价地图 在机器人进行路径规划时,我们需要明白规划算法是依靠什么在地图上来计算出来一条路径的。依靠的是gmapping扫描构建的一张环境全局地图,但是仅仅依靠一张原始的全局地图是不行的。因为这张地图是静态的,无法随时来更新地图上的障碍物信息。在现实环境中,总会有各种无法预料到的新障碍物出现在当前地图中,或者旧的障碍物现在已经从环境地图中被移除掉了,那么我们就需要来随...

JDWell的博客 1万+

机器人导航算法——Costmap地图ROS源码解析

costmap使用了一种分层地图的技术方案,即分别考虑障碍物层/膨胀层/静态障碍物层更新对应层的地图代价信息,然后再合并到主地图中,具体见我翻译的另一篇文章《costmap文献阅读—Layered Costmaps for Context-Sensitive Navigation以上就是costmap的介绍,后续会持续更新。。。。ReferenceCostmap文献阅读——Layered Costmaps for Context-Sensitive Navigation。

qq_40464599的博客 2982

arcgis密度分析

密度分析 密度分析是指根据输入的要素数据集计算整个区域的数据集状况,从而产生一个连续的密度表面。通过计算密度,将每个采样点的值散布到整个研究区域,并获得输出栅格中每个像元的密度值。在 ArcGIS 中,分布密度的计算方法有点密度分析、线密度分析和核密度分析三种。 1.点密度分析 导入实验数据居民点图层和道路图层 在自定义里勾选空间分析模块Spatial Analyst 点击空间分析工具中密度分析内的点密度分析, 参数设置如下,其中输出像元大小表示输出栅格数据集的像元大小。值越小.

Jasenjane的博客 2万+

ros中的costmap

直到我整理完move_base后才发现costmap也十分重要,才有了这篇文章。 costmap是一个package用于move_base中的global_map和local_map中。用于将2d/3d的传感器数据转化成一个2d的网格地图 1.总览 简单来说,地图中分成几部分 灰色部分:安全区域,robot运动在该区域不会发生碰撞 红色部分:危险区域,robot的footpr

sunyoop的博客 6293

基于电子海图的水面无人艇全局路径规划

Research and Implementation of Global Path Planning for Unmanned Surface Vehicle Based on Electronic Chart (基于电子海图的水面无人艇全局路径规划)   该论文已经在ICMIR2017会议上发表,附上springer的文献地址 Research and Implementation of Gl...

weixin_30797199的博客 1591

【ROS-Navigation-costmap_2d】costmap_prohibition_layer障碍物插件

系列文章目录 文章目录系列文章目录前言一、costmap_2d是什么?二、使用步骤1.下载源代码2.安装插件3.在costmap_2d中插入障碍物4.修改launch文件5.设置障碍物坐标参数6.主要事项总结 前言 随着SLAM的不断发展,机器人这门行业也越来越重要,很多人都开启了学习机器人,本文就介绍了ROS机器人操作系统的SLAM导航方向的navigation导航包中的costmap_2d。 以下是添加一个自定义的障碍物插件的流程 一、costmap_2d是什么? costmap_2d是

wesigj的博客 4229

HPE磁盘阵列管理04——MSA事件

本文介绍了HPE MSA存储系统的事件处理机制,重点分析了常见磁盘故障事件及其解决方案。文章首先定义了MSA事件的五个严重级别(严重、错误、警告、信息和解决),然后详细列举了多个典型事件案例(如事件1、3、6、8、172等),包括每种事件的触发条件、对系统的影响以及具体修复步骤。针对磁盘故障场景,文章提供了更换磁盘、重建磁盘组、取消隔离等操作建议,并强调应及时配置备用磁盘以降低数据风险。最后指出更详细的事件说明可参考《MSA事件描述参考指南》,并提供了HPE官方手册下载链接。全文为技术人员处理MSA存储故障

istrangeboy&begin zero的博客 1123

逆变器专题(9)-基于dq坐标系的逆变器解耦控制建模与实时仿真分析

本文深入探讨了基于dq坐标系的逆变器解耦控制建模与实时仿真分析。通过生动的比喻和详细的数学推导,阐述了如何通过坐标变换和前馈补偿实现d轴与q轴的独立控制,从而提升系统动态性能与稳定性。文章还介绍了在MATLAB/Simulink中搭建仿真模型、分析动态响应与稳定性的方法,并展望了硬件在环(HIL)实时仿真的高级验证手段,为新能源并网与电机驱动领域的工程师提供了宝贵的实践指南。

gold的博客 548

ros 导航中出现的costmap

costmap( 代价地图)   costmap是Navigation Stack里的代价地图,它其实也是move_base插件,本质上是C++的动态链接库,用过catkin_make之后生成.so文件,然后move_base在启动时会通过动态加载的方式调用其中的函数。 costmap是一个package是机器人收集传感器信息建立和更新的二维或三维地图,用在move_base的global_...

D学习中- 5432

数据中台:大数据平台,数据仓库(DM),数据中台之间的联系以及异同分析

大数据平台是一个技术平台。这个技术平台提供了对于大数据的分布式采集,存储,流处理和计算,实时分析等能力。在没有大数据平台前也有数据集成和管理的平台,这种平台可以实现对结构化数据本身的采集,集成和管理。 管理平台,是在原生的大数据生态的基础之上,为了更好的管理集群服务,管理集群的资源,提供灵活SRE能力和资源核算审计能力的一系列工具和合称整体架构数据中台包括数据仓库的全部内容,数据仓库为数据中台提供了数据对外提供服务的基础资源,数据中台将数据仓库建设的投入价值进行最大化,以加快数据赋能业务的速度大家都知道数据

GIS摆渡人 2136

【ROS-Navigation】Costmap2D代价地图源码解读-1

记录学习阅读ROS Navigation源码的理解,本文为Costmap2D代价地图源码学习记录,以文字总结、绘制结构图说明、代码注释为主。仍在学习过程中,有错误欢迎指正,共同进步。 Costmap通过各层地图订阅话题、接收传感器数据,维护各层地图数据,并最终整合出一张用于路径规划的主地图。 【结构示意图】 【相关文件】 costmap_2d/src/costmap_2d_r...

NEO's NOTEBOOK 5990

YOLOv8+BiFPN双向特征金字塔:多尺度目标检测精度提升28%的实战教程

双向特征金字塔网络(BiFPN)是一种强化多尺度特征融合支持“自顶向下+自底向上”的双向特征流动,同时保留不同尺度的细节信息;引入加权融合机制,自动学习不同特征的重要性权重;裁剪冗余节点,在轻量化的同时提升融合效率。

m0_64661770的博客 493

uniapp ios原生插件开发 (framework,cocoapods)

已知UniApp的插件开发方式有两种, 第一种 Xcode Framework的方式,这种方式是官方指定的方式。 这种方式的优点就是简单直接, 但也有不足,比如当插件需要引入一些三方库时,操作起来就不是那么方便。 而使用Cocoapods则可以很方便的引入三方库。 接下来,本文探索使用Cocoapods的方式来进行UniApp插件开发。

Rey的技术博客 9825

[ROS2] 你应该知道Costmap_2d 的这些细节

Costmap_2d 的插件 Costmap_2d 的插件都是继承于CostmapLayer。具体的关系如下图所示: StaticLayer StaticLayer内主要是通过接收map_server发布的地图话题来加载静态地图的。所以StaticLayer内是可以在线更改静态地图的。 ObstacleLayer ObservationBuffer ObservationBuffer 是一个障碍物观察数据的buffer。观测到的障碍物数据都将转成sensor_msgs::msg::PointCloud2格

首飞的博客 2261

一文读懂 CST 时/频域求解器

本文系统介绍了CST Studio Suite中的关键网格技术——六面体网格、四面体网格以及TLM求解器专用的八叉树非均匀网格技术。重点阐述了六面体网格的三项核心技术:理想边界拟合(PBA)技术可精确处理曲面边界,薄片技术(TST)能高效模拟薄层结构,自适应八叉树网格实现计算资源最优分配。同时详细对比了六面体网格与四面体网格的特点及适用场景,前者适用于系统级EMC/EMI分析等时域问题,后者擅长处理复杂曲面和异质材料的频域问题。

一只豌豆象的博客 470

学习costmap代价地图

0x00 什么是costmap代价地图 在机器人进行路径规划时,我们需要明白规划算法是依靠什么在地图上来计算出来一条路径的。依靠的是gmapping扫描构建的一张环境全局地图,但是仅仅依靠一张原始的全局地图是不行的。因为这张地图是静态的,无法随时来更新地图上的障碍物信息。在现实环境中,总会有各种无法预料到的新障碍物出现在当前地图中,或者旧的障碍物现在已经从环境地图中被移除掉了,那么我们就...

weixin_42005898的博客 6578

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

数学建模模型总结

这是本人在两年内准备参加数学建模竞赛搜集到的模型资料,已经经过了本人的筛选和整理,希望能够对准备参加数学建模竞赛的学弟学妹们提供一些帮助!

【ROS】使用pluginlib自定义costmap地图层

pluginlib是一个 C++ 库,用于从 ROS 包中加载和卸载插件。插件是从运行时库(即共享对象、动态链接库)加载的动态可加载类。使用 pluginlib,人们不必将他们的应用程序显式链接到包含类的库,相反,pluginlib 可以在任何时候打开一个包含导出类的库,而无需应用程序事先知道该库或包含类定义的头文件. 插件可用于在不需要应用程序源代码的情况下扩展/修改应用程序行为。

qq_52785580的博客 2276

efm32 入门.pdf

本PDF共计22页,介绍的是操作驱动API,下载与否自己斟酌。

上一篇: 查看Action 信息的常用命令
下一篇: [ROS2] map_server加载地图文件的三种模式
首飞爱玩机器人
博客等级 码龄14年 6990粉丝 120原创
评论 2
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

首飞爱玩机器人

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值