LeGO-Loam代码解析(一) 项目介绍、论文解读、配置安装

news2025/1/18 17:03:15

目录

1.项目介绍

2. 论文解读  LeGO-LOAM:轻量级且地面优化的可变地形激光里程计与建图

2.1 摘要

2.2 介绍

2.3 正文部分1 --- System Review

2.4 正文部分2 --- Segmatation(地面点角面点分离)

2.5  Feature Extraction 正文部分3 --- 特征提取

2.6 Lidar Odom 正文部分4 --- 前端里程计

2.7 Liadr Mapping 正文部分5 --- 后端优化

3 项目配置及编译问题解决


1.项目介绍

        LeGO-LOAM 是 Tixiao Shan 提出的一种基于 LOAM 的改进版本,其主要是为了实现
小车在多变地形下的定位和建图,其针对前端和后端都做了一系列的改进,具体来说:
        前端
1. 对地面点进行分类和提取,避免一些一场边缘点的提取
2. 应用了一个简单的点云聚类算法,剔除了一些可能的 outlier
3. 两步迭代求解前端帧间里程记,不影响精度的情况下减轻计算负载,保障了嵌入式平台的实时性

        后端
1. 使用 slam 中关键帧的概念对后端部分进行了重构
2. 引入回环检测和位姿图优化概念,使得地图的全局一致性更好

        最后,通过融合 [t_z, \theta_{roll},\theta_{pitch}][t_x,t_y,\theta_{yaw}]找到两次连续扫描之间的6D变换。通过使用所提出的两步优化方法,我们观察到可以实现类似的精度,同时计算时间减少了约35%(表III)。

2. 论文解读  LeGO-LOAM:轻量级且地面优化的可变地形激光里程计与建图

2.1 摘要

        摘要—我们提出了一种轻量级且地面优化的激光里程计与建图方法,称为LeGO-LOAM,用于实时地面车辆的六自由度姿态估计(要求雷达水平安装)。LeGO-LOAM是轻量级的,因为它可以在低功耗嵌入式系统上实现实时姿态估计。LeGO-LOAM是地面优化的,因为它利用分割和优化步骤中地面平面的存在。

        我们首先应用点云分割来滤除噪音,并进行特征提取以获取显著的的平面和边缘特征。然后,一个两步的Levenberg-Marquardt优化方法使用这些平面和边缘特征来解决连续扫描之间六自由度变换的帧间里程计。我们使用从可变地形环境中的地面车辆收集的数据集将LeGO-LOAM的性能与现有方法LOAM进行比较,并显示LeGO-LOAM在减少计算成本的同时实现了类似或更好的精度。我们还将LeGO-LOAM集成到SLAM框架中,以消除因漂移引起的姿态估计误差,这在使用KITTI数据集进行了测试。

2.2 介绍

        在本工作中,我们追求为装备有3D激光雷达的地面车辆实现可靠的、实时的六自由度姿态估计,以一种适用于小规模嵌入式系统高效实现的方式。这样的任务有其不容易的原因。许多无人地面车辆(UGV)由于其尺寸有限,不具备悬挂系统或强大的计算单元。小型UGV在不同地形上行驶时经常遇到非平滑的运动(运行的时候存在颠簸),因此获取的数据常常会发生畸变。由于有限的重叠区域,两次连续扫描之间的可靠特征对应关系也很难找到,因为存在大的运动(较大的颠簸会使两帧之间的运动关联出现错误)。此外,从3D激光雷达接收到的大量点云数据对于使用有限的机载计算资源进行实时处理构成了挑战。

        当我们将LOAM用于这种任务时,在无人地面车辆(UGV)以平稳运动在稳定特征中运行,并且拥有足够的计算资源支持时,我们可以获得低漂移的运动估计。然而,当资源有限时,LOAM的性能会下降。由于需要计算密集的3D点云中每个点的曲率,在轻量级嵌入式系统上进行特征提取的更新频率可能无法始终跟上传感器的更新频率。在嘈杂的环境中操作UGV也对LOAM构成了挑战。由于激光雷达在小型UGV上的安装位置通常靠近地面,来自地面的传感器噪声可能是一个持续存在的问题。例如,草地反射可能导致高粗糙度值。因此,可能会从这些点中提取出不可靠的边缘特征。同样,也可能从树叶返回的点中提取出边缘或平面特征。这些特征通常对于扫描匹配来说是不可靠的,因为同一片草叶或叶子可能不会在两次连续的扫描中出现。使用这些特征可能导致不准确的配准和较大的漂移。

        因此,我们提出了一种轻量级且地面优化的LOAM(LeGO-LOAM),用于在复杂的可变地形环境中估计UGV的姿态。LeGO-LOAM是轻量级的,因为可以在嵌入式系统上实现实时的姿态估计和建图。我们进行点云分割,以丢弃可能在地面分离后代表不可靠特征的点。LeGO-LOAM还是地面优化的,因为我们引入了一个两步优化的姿态估计方法。从地面提取的平面特征在第一步中用于获取[t_z,\theta_{roll},\theta_{pitch}]。在第二步中,通过与分割点云提取的边缘特征匹配,获得其余的变换[t_x,t_y,\theta_{raw}]。我们还整合了执行闭环来纠正运动估计漂移的能力。本文的其余部分组织如下。第二部分介绍了用于实验的硬件。第三部分详细描述了所提出的方法。第四部分在各种室外环境下进行了一系列实验。

2.3 正文部分1 --- System Review

        所提出的框架概览如图1所示。系统从3D激光雷达接收输入,并输出6自由度姿态估计。整体系统分为五个模块。

        第一个模块是分割模块,它将单次扫描的点云投影到一个距离图像中进行分割。

        然后,分割后的点云被发送到特征提取模块。接下来,激光里程计使用前一个模块提取的特征来找到关联连续扫描的变换。这些特征在激光建图中进一步处理,将它们注册到全局点云地图中。最后,变换融合模块将激光里程计和激光建图的姿态估计结果合并,并输出最终的姿态估计。所提出的系统旨在相对于原始的广义LOAM框架,寻求改进地面车辆的效率和精度。以下是这些模块的详细介绍。

        "6自由度位姿"是描述物体在三维空间中位置和方向的能力。它包括沿三轴的平移和绕三轴的旋转,用于机器人、工程和计算机图形学中精确控制物体运动和定位。 

2.4 正文部分2 --- Segmatation(地面点角面点分离)

        设P_t =\{p_1,p_2,...,p_n\}为时刻t采集的点云,其中p_iP_t中的一个点。首先,P_t被投影到一个距离图像上。由于VLP-16的水平和垂直角分辨率分别为0.2°和2°,所以投影的距离图像的分辨率为1800x16(每根线1800个点,共16线)。P_t中的每个有效点p_i现在由距离图像中的一个唯一像素表示。与点p_i相关联的距离值r_i表示从相应点p_i到传感器的欧几里德距离。由于在许多环境中存在倾斜地形,我们不假设地面是平坦的。在分割之前,会对距离图像进行列优先评估,这可以看作是地面平面估计,以提取地面点。经过这个过程后,可能代表地面的点被标记为地面点,不用于分割。

        然后,对距离图像应用了一种基于图像的分割方法,将点云分成许多聚类。同一聚类中的点被赋予唯一标签。需要注意的是,地面点是一种特殊类型的聚类。将分割应用于点云可以提高处理效率和特征提取的准确性。假设机器人在嘈杂的环境中运行,小物体(例如树叶)可能形成微不足道且不可靠的特征,因为同一片叶子不太可能在两次连续扫描中出现。为了使用分割后的点云进行快速和可靠的特征提取,我们忽略了点数少于30个的聚类。图2显示了分割前后的点云可视化。原始点云包括许多点,这些点来自周围可能会产生不可靠特征的植被。

在嘈杂环境中的扫描的特征提取过程。原始点云如图(a)所示。在图(b)中,红色点被标记为地面点。其余的点是分割后保留的点。只保留树干..树叶点都被剔除掉了在图(c)中,蓝色和黄色点表示F e 和 F p 中的边缘和平面特征。在图(d)中,绿色和粉色点分别代表F e 和 F p 中的边缘和平面特征。

        在这个过程之后,只有可能代表大型物体(例如树干)和地面点的点被保留供进一步处理(如图2(b)所示)。与此同时,只有这些点被保存在距离图像中。我们还为每个点获得了三个属性:(1)它作为地面点或分割点的标签,(2)它在距离图像中的列和行索引,以及(3)它的距离值。这些属性将在接下来的模块中被利用。

2.5  Feature Extraction 正文部分3 --- 特征提取

        与其从原始点云中提取特征不同,我们从地面点和分割点中提取特征。设 S 为来自距离图像相同行的点 p i 的连续点集。S 中一半的点位于 p i 的两侧。在本文中,我们将 |S| 设置为 10。利用在分割期间计算的距离值,我们可以评估 S 中点 p i 的粗糙度,

        为了均匀地从各个方向提取特征,我们将距离图像在水平方向上分成若干相等的子图像。然后,根据它们的粗糙度值 c,对子图像中每一行的点进行排序。与 LOAM 类似,我们使用一个阈值 c th 来区分不同类型的特征。我们将 c 大于 c th 的点称为边缘特征,将 c 小于 c th 的点称为平面特征。然后,从子图像的每一行中选择具有最大 c 的 n F e 个不属于地面的边缘特征点。以相同方式选择具有最小 c 的 n F p 个平面特征点,它们可能被标记为地面点或分割点。设 F e 和 F p 分别为所有子图像中的边缘和平面特征的集合。这些特征在图2(d)中可视化。然后,从子图像的每一行中提取具有最大 c 的 n F e 个不属于地面的边缘特征。类似地,从子图像的每一行中提取具有最小 c 的 n F p 个平面特征,它们必须是地面点。设 F e 和 F p 分别为此过程中的所有边缘和平面特征的集合。在这里,我们将360°的距离图像分成了6个子图像。每个子图像的分辨率为300x16。选择 n F e、n F p、n F e 和 n F p 分别为2、4、40和80。

2.6 Lidar Odom 正文部分4 --- 前端里程计

        激光里程计模块估计了两个连续扫描之间的传感器运动。通过执行点对边和点对平面的扫描匹配,找到了两次扫描之间的变换。换句话说,我们需要从上一次扫描的特征集合中找到与这次扫描对应的特征。

        然而,我们注意到可以进行一些改进来提高特征匹配的准确性和效率:

        1) 标签匹配:由于 F_{e}^tF_{p}^t中的每个特征在分割后都被编码为其标签,我们只寻找在 F_{e}^{t-1}F_{p}^{t-1} 中具有相同标签的对应关系。对于 F_{p}^t 中的平面特征,在 F_{p}^{t-1} 中仅使用被标记为地面点的点来寻找一个平面块作为对应。对于 F_{e}^t 中的边缘特征,其对应的边缘线在 F_{e}^{t-1} 的分割聚类中找到。通过这种方式找到对应关系可以提高匹配的准确性。换句话说,相同物体的匹配对应关系更有可能在两次扫描之间找到。这个过程也缩小了对应关系的潜在候选集。

        2) 两步L-M优化:在[20]中,编译了当前扫描中的边缘和平面特征点与它们在前一次扫描中的对应关系之间距离的一系列非线性表达式,形成一个综合距离向量。应用Levenberg-Marquardt(L-M)方法来找到两次连续扫描之间的最小距离变换。

        我们在这里引入了一个两步的L-M优化方法。在两步中找到最优的变换T:

        (1) 通过匹配 F_{p}^t中的平面特征和它们在 F_{e}^{t-1} 中的对应关系来估计[t_z, \theta_{roll},\theta_{pitch}]

        (2) 再使用 F_{e}^t中的边缘特征和它们在 F_{p}^{t-1} 中的对应关系来估计剩余的[t_x,t_y,\theta_{yaw}],同时以[t_z, \theta_{roll},\theta_{pitch}] 作为约束。需要注意的是,尽管[t_x,t_y,\theta_{yaw}]也可以从第一步优化中获得,但它们的准确性较低,不用于第二步。

        最后,通过融合 [t_z, \theta_{roll},\theta_{pitch}][t_x,t_y,\theta_{yaw}]找到两次连续扫描之间的6D变换。通过使用所提出的两步优化方法,我们观察到可以实现类似的精度,同时计算时间减少了约35%(表III)。

激光里程计模块的两步优化。首先通过匹配从地面点提取的平面特征获得 [t z , θ roll , θ pitch ]。然后,使用从分割点提取的边缘特征来估计 [t x , t y , θ yaw ],同时将 [t z , θ roll , θ pitch ] 作为约束。

2.7 Liadr Mapping 正文部分5 --- 后端优化

        激光建图模块将特征 \{ F_e^{t}, F_e^{p} \}与周围的点云地图 \bar{\mathbb{Q}}^{t-1} 进行匹配,以进一步优化姿态变换,但运行频率较低。然后,再次在此处使用 L-M 方法来获得最终的变换。

        LeGO-LOAM的主要区别在于最终点云地图的存储方式。与保存单个点云地图不同,我们保存每个独立的特征集\{ F_e^{t}, F_e^{p} \}。令M^{t-1} = \{ \{ F_e^1,F_p^1 \} ,...,\{ F_e^{t-1},F_p^{t-1} \} \}为保存所有先前特征集的集合。M^{t-1}中的每个特征集也与传感器在扫描时的姿态相关联。然后,\bar{\mathbb{Q}}^{t-1}可以从M^{t-1}中以两种方式获得。

        在第一种方法中,\bar{\mathbb{Q}}^{t-1}是通过选择传感器视野范围内的特征集来获得的。为简单起见,我们可以选择传感器姿态在当前传感器位置附近100米范围内的特征集。然后,选择的特征集被转换并融合成一个单独的周围地图\bar{\mathbb{Q}}^{t-1}

        我们还可以将位姿图(pose-graph)SLAM集成到LeGO-LOAM中。每个特征集的传感器姿态可以被建模为位姿图中的一个节点。特征集\{ F_e^{t}, F_e^{p} \}可以被视为这个节点的传感器测量。由于激光建图模块的姿态估计漂移非常小,我们可以假设在短时间内没有漂移。通过这种方式,可以通过选择一组近期的特征集来形成\bar{\mathbb{Q}}^{t-1},即Q^{t-1} = \{ \{ F_e^{t-k},F_p^{t-k} \} ,...,\{ F_e^{t-1},F_p^{t-1} \} \}, 其中 k 定义了 \bar{\mathbb{Q}}^{t-1} 的大小。然后,可以使用L-M优化后获得的变换将新节点 t−1 与 Q 中选择的节点之间添加空间约束。我们还可以通过执行闭环检测来进一步消除该模块中的漂移。在这种情况下,如果当前特征集与之前的特征集之间存在匹配,可以使用ICP(Iterative Closest Point)添加新的约束。然后,通过将位姿图发送到优化系统来更新传感器的估计姿态。

3 项目配置及编译问题解决

        本人计算机为Y9000K 2022 3080Ti电脑,Ubuntu版本为18.04.06,ROS版本为ROS melodic。

        Lego-LOAM依赖gtsam库,作者用的是gtsam4.0.0,但是lio-sam、lvi-sam用的gtsam为4.0.2,这里我安装gtsam4.0.2依旧可以编译运行。

        在编译时会遇到如下问题:

/usr/include/flann/ext/lz4.h:249:72: error: conflicting declaration ‘typedef struct LZ4_streamDecode_t LZ4_streamDecode_t’
 typedef struct { unsigned long long table[LZ4_STREAMDECODESIZE_U64]; } LZ4_streamDecode_t;

        解决方法是建立软链接:

sudo mv /usr/include/flann/ext/lz4.h /usr/include/flann/ext/lz4.h.bak
sudo mv /usr/include/flann/ext/lz4hc.h /usr/include/flann/ext/lz4hc.h.bak

sudo ln -s /usr/include/lz4.h /usr/include/flann/ext/lz4.h
sudo ln -s /usr/include/lz4hc.h /usr/include/flann/ext/lz4hc.h

        运行即可

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/896128.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

QT Quick之quick与C++混合编程

Qt quick能够生成非常绚丽界面,但有其局限性的,对于一些业务逻辑和复杂算法,比如低阶的网络编程如 QTcpSocket ,多线程,又如 XML 文档处理类库 QXmlStreamReader / QXmlStreamWriter 等等,在 QML 中要么不可…

【操作系统考点汇集】操作系统考点汇集

关于操作系统可能考察的知识点 操作系统基本原理 什么是操作系统? 操作系统是指控制和管理整个计算机系统的硬件和软件资源,并合理地组织调度计算机的工作和资源的分配,以提供给用户和它软件方便的接口和环境,是计算机系统中最基…

【C语言学习】参数传递

调用函数 1.如果函数有参数,调用函数时必须传递给它数量、类型正确的的值。 2.可以传递给函数的值是表达式的结果,包括: 字面量 变量 函数的返回值 计算的结果 int a,b,c; a5; b6; cmax(10,12); cmax(a,b); cmax(c,23); cmax(max(23,45),a);…

opencv实战项目-停车位计数

手势识别系列文章目录 手势识别是一种人机交互技术,通过识别人的手势动作,从而实现对计算机、智能手机、智能电视等设备的操作和控制。 1. opencv实现手部追踪(定位手部关键点) 2.opencv实战项目 实现手势跟踪并返回位置信息&a…

前端基础(JavaScript语法)

前言:今天学习JavaScript的基本语法,包括变量、函数、对象、数组。 目录 JavaScript 变量 函数 对象 数组 JavaScript 变量 定义变量 判断语句 判断等于: 判断不等于:! if else语句 if(vavb){ console.log("…

Harmony OS教程学习笔记

基础知识 1.如何修改程序启动的第一个页面? 不想使用创建的默认的页面,这时需要修改启动页面,修改的地方在EntryAbility文件中的onWindowStageCreate方法中。 onWindowStageCreate(windowStage: window.WindowStage) {// Main window is cr…

解决无法访问 Github 问题

GitHub作为程序员访问最频繁的网站,程序员们经常需要访问 Github找开源项目、学习新框架、管理自己的个人开源项目等等。 github加速器 因为GitHub属于国外的网站,直接访问的话,速度非常慢,甚至访问不了, 今天给大家…

centos下使用jemalloc解决Mysql内存泄漏问题

参考: MySQL bug:https://bugs.mysql.com/bug.php?id83047&tdsourcetags_pcqq_aiomsg https://github.com/jemalloc/jemalloc/blob/dev/INSTALL.md (1)ptmalloc 是glibc的内存分配管理 (2)tcmalloc…

如何批量修改图片名为不同名称

如何批量修改图片名为不同名称?当今社会,因为人们都养成了随手拍照的习惯,所以拥有上千上万张照片的相册已经司空见惯不足为奇。然而,我们在保存这些照片时往往都会碰到一个大难题——电脑中的图片名称千奇百怪,让整个…

打开软件提示mfc100u.dll缺失是什么意思?要怎么处理?

当你打开某个软件或者运行游戏,系统提示mfc100u.dll丢失,此时这个软件或者游戏根本无法运行。其实,mfc100u.dll是动态库文件,它是VS2010编译的软件所产生的,如果电脑运行程序时提示缺少mfc100u.dll文件,程序…

由“美”出发 听艺术家林曦关于美育与智慧的探讨

不久前,林曦老师与我们的老朋友「十点读书」进行了一次线上直播,有关林曦老师十余年的书法教学,和传统美育的心得,以及因此诞生的新书《无用之美》。      这一次的直播,由“美”的主题出发,延伸出美育…

微服务参数透传实现

说明:在微服务架构中,用户身份经网关验证后,我们可以将用户信息,如ID加入到请求头上。后面的微服务中,可以设置一个拦截器,拦截请求,获取请求头上的用户ID,加入到ThreadLocal中。 最…

Spring【学习记录一】

Spring内容解释 早期的Spring仅指代Spring Framework,后来基于Spring Framework孵化出大量的项目,Spring的含义变成了指代Spring家族 Spring Framework是Spring家族所有成员的基础,想要学透Spring,就必须要掌握Spring Framework…

电脑提示concrt140.dll丢失或找不到怎么恢复

现在系统在安装的时候为了简化包体会将一些组件给删除了,这样会造成在运行某些程序的时候,出现组件丢失的提示。例如concrt140.dll丢失,如果不及时处理,会导致系统中不少程序无法正常使用,那么要如何处理这个问题呢&am…

SpringBoot案例-员工管理-删除员工

查看页面原型,明确需求 页面原型 有批量删除和删除单个数据 需求 查看接口文档 接口文档的链接如下: 【腾讯文档】SpringBoot案例所需文档 https://docs.qq.com/doc/DUkRiTWVaUmFVck9N 思路分析 删除单个数据,将要删除的员工信息的id传…

消息中间件主要作用

首先我们想一下,两个公司之间如果有互相调用接口的业务需求,如果没有引入中间件技术,是怎么实现的呢? 用户发起请求给系统A,系统A接到请求直接调用系统B,系统B返回结果后,系统A才能返回结果给用…

YOLOv5、YOLOv8改进:S2注意力机制

目录 1.简介 2.YOLOv5改进 2.1增加以下S2-MLPv2.yaml文件 2.2common.py配置 2.3yolo.py配置 1.简介 S2-MLPv2注意力机制 最近,出现了基于 MLP 的视觉主干。与 CNN 和视觉Transformer相比,基于 MLP 的视觉架构具有较少的归纳偏差,在图像识…

线代强化第四章

下面正式开始公式的证明: B改变了矩阵的秩,所以他是不满秩的。 就是说一个矩阵如果左边乘上一个列满秩的,它的秩不会改变 一个矩阵如果右边乘上一个行满秩的,它的秩不会改变 PROVE: 等于主对角线或副对角线上分块阵的秩的和 当两…

Three.js 实现模型材质局部辉光效果和解决辉光影响场景背景图显示的问题

1.Three.js 实现模型材质局部辉光效果 2.解决辉光效果影响场景背景图显示的问题 相关API的使用: 1. EffectComposer(渲染后处理的通用框架,用于将多个渲染通道(pass)组合在一起创建特定的视觉效果) 2. …

【100天精通python】Day36:GUI界面编程_Tkinter高级功能操作和示例

目录 专栏导读 一、GUI 高级功能 1 自定义主题和样式 2 实现拖放功能 3 多线程和异步编程 二、实战项目 1. 待办事项应用 2. 图像查看器 3. 文本编辑器 4 添加动画和过渡效果 5 多界面和多线程示例 专栏导读 专栏订阅地址:https://blog.csdn.net/qq_358…