1. 环境准备打造一个兼容ORB SLAM2与3的Ubuntu20.04系统想在Ubuntu 20.04上同时玩转ORB SLAM2和ORB SLAM3听起来像是要在一台电脑上装两套不同的操作系统但其实没那么复杂。核心思路就是搭建一个“和平共处”的软件环境让两个框架都能找到它们各自需要的“食材”依赖库并且互不干扰。我折腾过好几次发现最关键的点在于依赖库版本的精确控制和路径的清晰管理。如果你一股脑用apt-get install装最新版的库十有八九会踩坑因为ORB SLAM2和3虽然同宗同源但对某些库的版本要求有细微差别尤其是Pangolin和OpenCV。首先给系统换源是必须的能省下大量下载等待时间。我习惯用清华源速度非常稳定。操作很简单备份好原来的sources.list文件然后替换成清华源的配置接着sudo apt-get update更新软件列表。这一步是基础确保后续安装过程顺畅。接下来我们需要安装一些编译工具比如git、gcc、g、cmake和make这些是编译任何开源项目的“螺丝刀”和“扳手”。直接用sudo apt-get install一条命令就能搞定。但真正的挑战从安装Pangolin开始。很多教程会建议你装最新版但根据我的经验对于ORB SLLAM2和3的共存环境Pangolin 0.6这个“稳定版”才是最佳选择。新版API可能有变动容易引发兼容性问题。从GitHub上克隆0.6版本后安装其依赖项要注意像libglew-dev、libboost-dev这些库都不能少。编译时记得加上-DCPP11_NO_BOOST1这个CMake选项这是为了处理一些C11标准的兼容性问题能避免后续一些莫名其妙的编译错误。编译安装后别忘了运行一下自带的HelloPangolin例子弹出一个旋转的立方体窗口就证明Pangolin安装成功了。这个小测试能帮你提前发现图形驱动之类的问题免得后面SLAM跑起来才发现窗口打不开。2. 核心依赖库的定制化安装与路径管理依赖库的安装不是简单地“装上去就行”而是要为后续两个SLAM框架的灵活调用做好准备。这里我们重点处理Eigen3和OpenCV。Eigen3是一个纯头文件的C模板库用于线性代数运算。安装它通常很简单从GitHub克隆源码编译安装即可。但有个小坑默认安装会把头文件放在/usr/local/include/eigen3/目录下。而ORB SLAM2在查找时可能会直接去/usr/local/include/下面找Eigen文件夹。所以我们需要手动把Eigen头文件复制或移动到上一级目录。这个操作很关键我当初就因为这个路径问题编译时一直报错找不到Eigen。OpenCV的安装则是整个环境搭建中最需要精心设计的一环。我们的目标是让ORB SLAM2和ORB SLAM3都能在需要的时候准确地找到我们安装的这个特定版本OpenCV 3.4.5而不是系统里可能存在的其他版本。我强烈推荐将OpenCV安装到自定义目录而不是默认的/usr/local。比如我在家目录下创建了一个Libs文件夹专门存放这些自定义安装的库这次就把OpenCV 3.4.5安装到/home/yourname/Libs/opencv-3.4.5。在CMake配置时通过-D CMAKE_INSTALL_PREFIX参数指定这个路径。这样做的好处是绝对的隔离性。安装完成后在这个自定义的安装路径下会有一个share/OpenCV/OpenCVConfig.cmake文件。这个文件就像是OpenCV的“身份证”和“住址簿”CMake在查找OpenCV时就是靠它。以后当我们在ORB SLAM2或3的CMakeLists.txt里通过set(OpenCV_DIR “/path/to/your/opencv/share/OpenCV”)指向这个文件CMake就会精准地使用我们安装的这个版本。完全不用担心干扰系统其他可能依赖OpenCV的程序。编译OpenCV是个耗时过程用make -j4或者make -j8可以利用多核加速具体数字取决于你CPU的核心数。3. ORB SLAM2的部署、编译与排坑实录环境准备好后我们就可以请出第一位主角了。从GitHub克隆ORB SLAM2的源码后先别急着运行build.sh。我建议先手动检查并修改两个关键的CMakeLists.txt文件一个是项目根目录下的另一个是Thirdparty/DBoW2目录下的。修改的核心目的就是告诉CMake“请使用我刚刚精心准备的那些库”。具体来说就是在find_package(OpenCV 3.0 QUIET)语句之前添加我们自定义的OpenCV路径。就像这样set(OpenCV_DIR /home/yourname/Libs/opencv-3.4.5/share/OpenCV)同时确保Eigen的查找语句是find_package(Eigen3 REQUIRED)。这些修改是为了绕过系统自动查找实现精准定位。接下来运行./build.sh脚本它会自动编译ORB SLAM2及其第三方依赖如DBoW2, g2o。但根据我的经验在Ubuntu 20.04上你大概率会遇到两个经典的编译错误。第一个是‘usleep’ was not declared in this scope这个错误在好几个源文件中都会出现。解决方法是在每一个报错的文件开头添加头文件#include unistd.h。这个函数声明在这个头文件里新系统或编译器环境可能要求显式包含。第二个错误更棘手一点static assertion failed: std::map must have the same value_type as its allocator。这个错误出现在include/LoopClosing.h文件中涉及到Eigen内存分配器与STL容器的模板匹配问题。你需要找到typedef mapKeyFrame*,g2o::Sim3...这一长串定义并将其替换为修正后的版本。修正的关键在于std::pair的模板参数要把const KeyFrame*改为KeyFrame *const。这个改动非常细微但却是解决这个编译错误的唯一方法。我当初查了好久才找到这个解决方案。成功解决这两个错误后再次编译应该就能顺利看到100%的完成提示了。4. ORB SLAM3的部署与编译要点ORB SLAM3的安装流程整体上和ORB SLAM2类似因为它本身就是后者的进化版。克隆源码后你会发现它的依赖要求有些许不同。ORB SLAM3需要Python 2.7的开发库这是因为它的一些脚本或工具可能还在用Python2。所以你需要先运行sudo apt install libpython2.7-dev来满足这个条件。同样在编译前也需要修改其CMakeLists.txt文件将OpenCV的路径指向我们自定义安装的3.4.5版本。ORB SLAM3的CMake脚本对OpenCV 4的支持更好一些但为了和ORB SLAM2保持一致避免未知问题我们坚持使用3.4.5。修改的位置和ORB SLAM2一样。运行./build.sh开始编译。ORB SLAM3的代码量更大编译时间会更长。在这个过程中你可能会遇到一个令人困惑的错误c: fatal error: Killed signal terminated program cc1plus。这通常不是代码错误而是系统内存或交换空间swap不足导致的。编译器进程被系统“杀死”了。解决方法是修改build.sh脚本降低编译并行度。把里面的make -j4或make -j改成make -j2甚至make单线程编译。虽然慢但能保证编译完成。编译成功后你就拥有了两套完整的SLAM系统。5. TUM数据集实战评测ORB SLAM2 vs ORB SLAM3环境搭好了两个系统也装好了是时候拉出来“跑跑分”了。我们选择TUM RGB-D数据集中的单目序列进行测试这是SLAM领域非常标准的“考场”。评测不是为了分个绝对的胜负而是直观感受两者的差异和演进。我选取了六个有代表性的序列包括纹理丰富的、快速旋转的、存在遮挡的和弱纹理的场景。测试命令是一样的以freiburg2_coke序列为例./Examples/Monocular/mono_tum Vocabulary/ORBvoc.txt Examples/Monocular/TUM2.yaml /path/to/rgbd_dataset_freiburg2_coke你需要根据序列所属的freiburg1/2/3来切换对应的TUM1/2/3.yaml配置文件并把路径替换成你自己数据集存放的位置。ORB SLAM2 测试表现freiburg2_coke可乐罐初始化非常缓慢相机需要来回移动很久才能成功初始化。运行过程中容易跟踪失败轨迹经常断裂。freiburg2_360_kidnap快速旋转与遮挡在快速旋转和人为遮挡时极易丢失跟踪。freiburg3_nostructure_texture_near_withloop平面纹理这是它的“舒适区”表现稳定能完成闭环效果不错。freiburg2_pioneer_360手持旋转初始化慢运动中容易跟丢。freiburg2_pioneer_slam3和freiburg3_large_cabinet弱纹理场景基本无法初始化或很快跟踪失败。ORB SLAM3 测试表现freiburg2_coke最明显的改进初始化速度显著快于ORB SLAM2。虽然在运动过程中也有跟踪失败的情况但我观察到它重定位Relocalization的能力更强了失败后能更快地找回姿态让轨迹得以延续。freiburg2_360_kidnap面对遮挡和旋转仍然有挑战轨迹会出现跳变但整体鲁棒性感觉稍有提升。freiburg3_nostructure_texture_near_withloop和ORB SLAM2一样稳定这是基础能力。freiburg2_pioneer_360多次跟丢但通过重定位机制又能恢复轨迹断断续续。freiburg2_pioneer_slam3和freiburg3_large_cabinet在极端弱纹理下依然很困难未能生成有效轨迹。6. 深度对比分析与个人经验分享通过上面这些实际测试我们可以得出一些比较实在的结论。ORB SLAM3在初始化阶段的优化是实实在在的这得益于它可能采用了更高效的初始位姿估计策略。在纹理一般的场景下你能明显感觉到它更快地“抓住”了环境这是体验上的一个巨大提升。另一个核心改进是重定位模块。在跟踪丢失后ORB SLAM3似乎有更大的概率找回正确的相机位置。这背后可能是使用了更强大的场景识别算法或者更高效的词袋模型匹配。在实际应用中这个特性非常宝贵意味着系统在短暂遮挡或快速运动后更有可能“自救”成功而不是彻底崩溃需要重启。但是我们也要看到它的局限。在手持快速旋转、剧烈运动或者极端弱纹理的环境下无论是ORB SLAM2还是3都仍然会面临严峻挑战。纯视觉SLAM的固有难题——对光照、纹理和运动速度的敏感性——并没有被根本解决。ORB SLAM3的改进更像是在原有框架上的“精装修”提升了稳定性和用户体验但地基纯视觉的限制还在。关于多版本共存的管理我最后的建议是养成好习惯。像Pangolin、OpenCV这样被多个项目依赖的库尽量采用从源码编译安装到自定义路径的方式。在每个项目的CMakeLists.txt里显式地指定这些库的路径。这样你的系统就像一个整洁的工具箱每个项目都知道自己的工具放在哪不会拿错。虽然第一次设置稍微麻烦点但后期维护和切换版本会异常轻松完全不用担心依赖冲突的问题。这种管理方式在我后续尝试其他视觉SLAM算法如VINS-Mono、LSD-SLAM时也带来了极大的便利。