前言前端
目前机器人使用中须要进行SLAM建图,由于移动机器人想要实现自主行走,核心在于实现自主定位导航,在自主定位导航技术中会涉及到定位、建图、路径规划等问题,而地图构建的好坏将直接影响机器人的行走路径。机器人想要到达某个目的地,须要和人类绘制地图同样,描述环境、认识环境的过程主要就是依靠地图。node
而目前建图方式有激光雷达、视觉建图、还有深度学习等。今天介绍的cartographer就属于激光slam。主流的激光SLAM算法有hector、gmapping、karto、cartographer等。python
下面简单的介绍几种SLAM算法:linux
1. hector是一种结合了鲁棒性较好的扫描匹方法2D_SLAM方法和使用惯性传感系统的导航技术。传感器的要求较高,高更新频率小测量噪声的激光扫描仪,不须要里程计。使空中无人机与地面小车在不平坦区域运行存在运用的可能性。做者利用现代激光雷达的高更新率和低距离测量噪声,经过扫描匹配实时地对机器人运动进行估计。因此当只有低更新率的激光传感器时,即使测距估计很精确,对该系统都会出现必定的问题。nginx
hector基于优化的算法(解最小二乘问题),优缺点:不须要里程计,但对于雷达帧率要求很高40Hz,估计6自由度位姿,能够适应空中或者地面不平坦的状况。初值的选择对结果影响很大,因此要求雷达帧率较高。 c++
2. gmapping是一种基于粒子滤波的激光SLAM算法,它已经集成在ROS中,是移动机器人中使用最多的SLAM算法。基于粒子滤波的算法用许多加权粒子表示路径的后验几率,每一个粒子都给出一个重要性因子。可是,它们一般须要大量的粒子才能得到比较好的的结果,从而增长该算法的的计算复杂性。此外,与PF重采样过程相关的粒子退化耗尽问题也下降了算法的准确性。git
缺点:严重依赖里程计,没法适应无人机及地面不平坦的区域,无回环(激光SLAM很难作回环检测),大的场景,粒子较多的状况下,特别消耗资源。github
3. karto是基于图优化的SLAM算法,用高度优化和非迭代cholesky矩阵进行稀疏系统解耦做为解。图优化方法利用图的均值表示地图,每一个节点表示机器人轨迹的一个位置点和传感器测量数据集,箭头的指向的链接表示连续机器人位置点的运动,每一个新节点加入,地图就会依据空间中的节点箭头的约束进行计算更新。路标landmark越多,内存需求越大,然而图优化方式相比其余方法在大环境下制图优点更大。算法
karto采起的是spa(karto_slam)或g2o(nav2d), karto的前端与后端采起的是单线程进行。sql
4.LagoSLAM 是线性近似图优化,不须要初始假设。基本的图优化slam的方法就是利用最小化非线性非凸代价函数.每次迭代, 解决局部凸近似的初始问题来更新图配置,过程迭代必定次数直到局部最小代价函数达到. (假设起始点通过屡次迭代使得局部代价函数最小). 。假设图中每一个节点的相对位置和方向都是独立的,做者求解了一个等价于非凸代价函数的方程组。为此,提出了一套基于图论的程序,经过线性定位和线性位置估计,获得非线性系统的一阶近似。
5. cartographer是google开发的实时室内SLAM项目,cartographer采用基于google自家开发的ceres非线性优化的方法,cartographer的亮点在于代码规范与工程化,很是适合于商业应用和再开发。而且cartographer基于submap子图构建全局地图的思想,能有效的避免建图过程当中环境中移动物体的干扰。而且cartographer支持多传感器数据(odometry、IMU、LaserScan等)建图,支持2D_SLAM和3D_SLAM建图。
能自然的输出协方差矩阵,后端优化的输入项。成本较低的雷达也能跑出不错的效果。cartographer是google推出的一套基于图优化的SLAM算法。
cartographer算法并无给人惊艳的感受,但该算法的主要目标是实现低计算资源消耗,达到实时SLAM的目的,因此很适合嵌入式端的使用。
这篇文章是介绍cartographer在linuxPC环境(Ubuntu16)下进行源码下载进行demo测试的教程,本文的前提条件是你的电脑里已经安装了ROS如下版本的任意一个:Noetic、Kinetic、Melodic。
算法分析
该算法主要分为两个部分,第一个部分称为Local SLAM, 该部分经过一帧帧的Laser Scan创建并维护一系列的Submap,而所谓的submap就是一系列的Grid Map。当再有新的Laser Scan中会经过Ceres Scan Matching的方法将其插入到子图中的最佳位置。可是submap会产生偏差累积的问题,所以,算法的第二个部分,称为Global SLAM的部分,就是经过Loop Closure来进行闭环检测,来消除累积偏差:当一个submap构建完成,也就是不会再有新的laser scan插入到该submap时,算法会将该submap加入到闭环检测中。闭环检测的本质也是一个优化问题,该优化问题被表达成了一个pixel-accurate match的形式,解决优化问题的方法是Branch-and-Bound Approach.
做者:良知犹存
转载受权以及围观:欢迎添加微信公众号:羽林君
安装介绍
cartographer的安装主要包括三个部分:cartographer、cartographer-ros、ceres-solver。其中cartographer 是计算的部分,cartographer-ros是算法在ROS中通信交互数据的部分,ceres-solver谷歌开发的一款用于非线性优化的库,在谷歌的开源激光雷达slam项目cartographer中被大量使用。
安装的方法有两种,一种是官网的集成式下载配置,一种是把cartographer须要的依赖部分分别安装配置。
两种方式区别就在于,第一种虽然方便,可是因为网络问题(你懂的)因此Google的相关文件下载会失败,因此就出现了,把依赖单独下载编译,最后下载cartographer进行编译。
官网方式:
1. 安装 wstool下载工具、rosdep和ninja编译工具(ninja是一个新型的编译小工具,用来替换复杂的make,从而实现快速编译)
2. 创建一个wstool下载+ROS基本编译的二合一环境
这是 wstool 命令生成 .rosinstall 的文件里面的内容,能够看到设置了cartographer、cartographer-ros下载连接。
静静等待下载,速度就取决你对于Google的认知。
3.安装proto3.
Protocol Buffers(简称Protobuf) ,是Google出品的序列化框架,与开发语言无关,和平台无关,具备良好的可扩展性。Protobuf和全部的序列化框架同样,均可以用于数据存储、通信协议。
此外其实除了Protobuf咱们还能够配置其余依赖,这些脚本都在这个目录,若是编译过程当中遇到依赖问题就能够去利用脚本去下载。
4.rosdep init在安装ROS时候就安装过了,不过这个常常会出现问题,我以前写过一篇ROS安装的文件,你们有兴趣能够去看看
对于这个问题,有两种解决思路:访问DNS解析环节解决或者直接切换软件源。
DNS解析环节解决:
切换linux软件源:
5.最后一步编译
可是好多时候由于下载问题,就会出现这样那样的问题,因此就出现了下面的方法,把包单独下载,而后再进行编译安装。
注!:在我编译cartographer过程当中,和文章所写这种一鼓作气的感受偏偏相反,我编译了好屡次才编译成功的,并且中间出现各类编译问题,基本都是版本问题。因此请你们注意下载各个分包的版本,切记,切记,切记~
你看我probuf版本下载记录就知道了。
分包编译方式:
cartographer分红6个部分,分别是eigen3.2.9,ceres1.13.0,protobuf大于3.0.0,cartographer,cartogpher_ros,abseil。分开进行编译:
1.eigen
Eigen是高级 C ++ 模板标头库,用于线性代数,矩阵和矢量运算,几何变换,数值求解器和相关算法。自3.1.1版以来,Eigen是根据Mozilla Public License 2.0许可的开源软件。早期版本是根据GNU较宽松通用公共许可证受权的。
注意警告:cartographer对eigen,ceres,protobuf有严格的版本限制,版本必须严格!!!
安装完成
2.ceres
Ceres solver 是谷歌开发的一款用于非线性优化的库,在谷歌的开源激光雷达slam项目cartographer中被大量使用。
注意:ceres版本必须是1.13.0,其它版本与eigen3.2.9不匹配
编译过程当中若是出现这个编译问题:
Failed to find glog
-- Failed to find installed glog CMake configuration, searching for glog build directories exported with CMake.
-- Failed to find an installed/exported CMake configuration for glog, will perform search for installed glog components.
-- Failed to find glog - Could not find glog include directory, set GLOG_INCLUDE_DIR to directory containing glog/logging.h
这个缘由是缺失glog库(glog 是一个 C++ 日志库,它提供 C++ 流式风格的 API。在安装 glog 以前须要先安装 gflags,这样 glog 就可使用 gflags 去解析命令行参数),咱们能够用apt-get install安装,也能够下载源码进行编译安装.
apt-get install安装:
下载源码进行编译安装:
再从新进行cere编译安装,又经过一关
3. protobuf
Protocol Buffers(简称Protobuf) ,是Google出品的序列化框架,与开发语言无关,和平台无关,具备良好的可扩展性。Protobuf和全部的序列化框架同样,均可以用于数据存储、通信协议。
注意:protobuf安装方式特殊,脚本安装
此次也会遇到error问题,
第一个error 48: autoreconf: not found
是在不一样版本的 tslib 下执行 autogen.sh 产生。它们产生的缘由同样,是由于没有安装automake 工具, 用下面的命令安装好就能够了。
第二个error多是下载问题,这边会提示你下载失败,你能够选择注释掉,或者使用我提供的第二种编译方法:
第二种编译方法:
上文说到,咱们在cartographer/scripts目录下能够找到cartographer依赖文件的下载的脚本,这些的脚本里面还有编译的选项,这时候咱们就能够看下install_proto3.sh 这个文件,里面能够看到以下内容:
咱们直接复制直接编译便可。
4.abseil
abseil 是 google 开源的 C++通用库,其目标是做为标准库的补充。abseil 不但提供了标准库没有但很经常使用的功能,也对标准库的一些功能进行了加强设计,使用 abseil 库能使程序性能和开发效率都取得不错的提高。
cartographer对abseil没有版本要求,可是必定要有。
不过在后续编译abseil,你们可能会遇到这个问题
CMake Error at CMakeLists.txt:49 (find_package):
By not providing "FindAbseil.cmake" in CMAKE_MODULE_PATH this project has
asked CMake to find a package configuration file provided by "Abseil", but
CMake did not find one.
Could not find a package configuration file provided by "Abseil" with any
of the following names:
AbseilConfig.cmake
abseil-config.cmake
Add the installation prefix of "Abseil" to CMAKE_PREFIX_PATH or set
"Abseil_DIR" to a directory containing one of the above files. If "Abseil"
provides a separate development package or SDK, be sure it has been
installed.
不过没事,是由于CMakeLists.txt在进行搜寻absil中,定义的名称和你编译abseil名称不一样,CMakeLists.txt是大写的,而实际你编译安装后的包名称为小写。
修改如上所示:Abseil 修改成 absl
5.carographer
注意:carographer和cartographer _ros版本必须对应
编译成功:
建图开发
如今安装了Cartographer和Cartographer的ROS集成,官方也提供了一些数据集,Deutsches Museum(德意志博物馆),这样我就能够很方便测试Cartographer生成地图和其余的功能了。
下载示例包(例如德意志博物馆的2D和3D背包系列)到一个已知的位置
示例位于~/Downloads,并使用roslaunch来调出演示:
又会是下载的问题,这些文件又大,下载速度又慢还常常失败,我也是废了九牛二虎之力下载下来的。
为了方便你们测试,你们能够公众号后台私我,或者添加我微信号,我把我下载好的文件发给你们。
截图有限,以前操做都忘记截图了,致使如今就只有一个了,你们凑合看了哈。
生成.pdstream地图(等待直到cartographer_offline_node完成),
而后运行纯定位:
此外还有turtlebot的数据,其实都是同样的,你们也能够看一下创客智造的cartographer_turtlebot教程。
这就是我分享的cartographer的简单测试使用,将来我会介绍更加详细的cartographer使用以及源码解析。此外若是你们有什么更好的思路,也欢迎分享交流哈。
—END—
推荐阅读
【1】linux开发各类I/O操做简析,以及select、poll、epoll机制的对比
【3】CPU中的程序是怎么运行起来的 必读
【4】什么?还不懂c++vector的用法,你凭什么勇气来的!
【5】阶段性文章总结分析
本公众号所有原创干货已整理成一个目录,回复[ 资源 ]便可得到。
申明以上部份内容是参考了别人的文章,若有侵权,请告知,我将删除!