要学会PCL首先要对C++进行学习,所以这里我们首先对PCL库的代码中常见的C++的技巧进行整理和概述,并且对其中的难点进行细化讲解。首先我们搞清楚PCL库的文件形式、是一个以CMake构建的项目,库中主要以cpp,.h,.hpp文件三种文件形式。那我们知道cpp是C++工程中函数实现的代码,以下是根据PCL库中的代码中常用的C++特征。基本介绍请查看文章:点云及PCL编程基础 .h和.hpp文件的区别 与*.h类似,hpp是C++程序头文件,其实质是将cpp中的实现代码放在.hpp文件中,定义与实现都包含在同一个文件中,在使用的时候只需要include 该hpp文件即可,无需将cpp加入到项目中进行编译,而实现代码将直接编译到调用者的obj文件中,不再单独生成obj,采用hpp将大幅度的减少调用项目中cpp文件数和编译次数,也不用发布lib或者dll,因此非常适合用来编写公开的开源库。 该文件具有的特点:
不可包含全局对象和全局函数:由于hpp本质上是作为.h被调用者include,所以当hpp文件中存在全局对象或者全局函数,而该hpp被多个调用者include时,将在链接时导致符号重定义错误。要避免这种情况,需要去除全局对象,将全局函数封装为类的静态方法。 类之间不可循环调用:在.h和.cpp的场景中,当两个类或者多个类之间有循环调用关系时,只要预先在头文件做被调用类的声明即可。在hpp场景中,由于定义与实现都已经存在于一个文件,调用者必需明确知道被调用者的所有定义,而不能等到cpp中去编译。因此hpp中必须整理类之间调用关系,不可产生循环调用。 不可使用静态成员:静态成员的使用限制在于如果类含有静态成员,则在hpp中必需加入静态成员初始化代码,当该hpp被多个文档include时,将产生符号重定义错误。唯 一的例外是const static整型成员。 #progma once 与ifndef的区别 为了避免同一个文件被include 多次,在能够支持这两种方式的编译器上,二者并没有太大的区别,但是两者仍然还是有一些细微的区别。
方式一由语言支持所以移植性好,方式二 可以避免名字冲突 C++模块类 模板是C++支持参数化多态的工具,使用模板可以使用户为类或者函数申明一种一般的模式,使得类中的某些数据成员或者成员函数的参数,返回值取得任意类型。 模板是一种对类型进行参数化的工具,通常有两种形式:函数模板和类模板。 函数模板针对仅参数类型不同的函数,类模板针对仅数据成员和成员函数类型不同的类。 注意:模板的申明或者定义智能在全局,命名空间或者类范围内进行,既不能在局部范围,函数内进行,比如不能在主函数中申请或者定义一个模板。 比如在common/centroid.h文件中 template <typename PointT, typename Scalar> inline unsigned int compute3DCentroid (ConstCloudIterator<PointT> &cloud_iterator, Eigen::Matrix<Scalar, 4, 1> ¢roid); 其中类模板和函数模板都是以template开始后接模板形参列表组成,模板形参不能为空,一但声明了类模板就可以用类模板的形参名声明类中的成员变量和成员函数,即可以在类中使用内置类型的地方都可以使用模板形参名来声明。 inline函数的作用 在C++中, 为了解决一些频繁调用的小涵数大量消耗栈空间或者是叫栈内存的问题,特别的引入了inline修饰符,表示为内联涵数。 inline的使用时有所限制的,inline只适合函数体内部代码简单的函数使用,不能包含复杂的结构控制语句例如while、switch,并且不能内联函数本身不能是直接递归函数(即,自己内部还调用自己的函数)。 关键字inline 必须与函数定义体放在一起才能使函数成为内联,仅将inline 放在函数声明前面不起任何作用。 extern“C”的作用 extern "C"的真实目的是实现类C和C++的混合编程。extern “C”是由C++提供的一个连接交换指定符号,用于告诉C++这段代码是C函数。extern “C”后面的函数不使用的C++的名字修饰,而是用C。这是因为C++编译后库中函数名会变得很长,与C生成的不一致,造成C++不能直接调用C函数。 #define PCL_EXPORTS __declspec(dllexport) 一般而言,动态链接库中定义有两种函数:导出函数(export function)和内部函数(internal function)。导出函数可以被其它模块调用,内部函数在定义它们的DLL程序内部使用。在要输出的函数、类、数据的声明前加上__declspec(dllexport)的修饰符,表示输出,导入修饰__declspec(dllimport),声明某个类、函数是从dll中导入的。 资源 三维点云论文及相关应用分享 【点云论文速读】基于激光雷达的里程计及3D点云地图中的定位方法 3D-MiniNet: 从点云中学习2D表示以实现快速有效的3D LIDAR语义分割(2020) PCL中outofcore模块---基于核外八叉树的大规模点云的显示 更多文章可查看:点云学习历史文章大汇总 SLAM及AR相关分享 |
|