要学会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文件类似,hpp也是C++程序的头文件。

是一般模板类的头文件

一般来说。.h文件只有申明,没有函数的实现,.hpp里申明与实现都有,后者可以减少cpp的数量

*.h里面可以有using namespace std,而*.hpp里尽量不要出现。

*.hpp要注意的问题有:

不可包含全局对象和全局函数:由于hpp本质上是作为.h被调用者include,所以当hpp文件中存在全局对象或者全局函数,而该hpp被多个调用者include时,将在链接时导致符号重定义错误。要避免这种情况,需要去除全局对象,将全局函数封装为类的静态方法。

类之间不可循环调用:在.h和.cpp的场景中,当两个类或者多个类之间有循环调用关系时,只要预先在头文件做被调用类的声明即可。在hpp场景中,由于定义与实现都已经存在于一个文件,调用者必需明确知道被调用者的所有定义,而不能等到cpp中去编译。因此hpp中必须整理类之间调用关系,不可产生循环调用。

不可使用静态成员:静态成员的使用限制在于如果类含有静态成员,则在hpp中必需加入静态成员初始化代码,当该hpp被多个文档include时,将产生符号重定义错误。唯 一的例外是const static整型成员。

#progma once 与ifndef的区别

为了避免同一个文件被include 多次,在能够支持这两种方式的编译器上,二者并没有太大的区别,但是两者仍然还是有一些细微的区别。

#ifndef的方式依赖于宏名字不能冲突,这不光可以保证同一个文件不会被包含多次,也能保证内容完全相同的两个文件不会被不小心同时包含。当然,缺点就是如果不同头文件的宏名不小心"撞车",可能就会导致头文件明明存在,编译器却硬说找不到声明的状况

#pragma once则由编译器提供保证:同一个文件不会被包含多次。注意这里所说的"同一个文件"是指物理上的一个文件,而不是指内容相同的两个文件。带来的好处是,你不必再费劲想个宏名了,当然也就不会出现宏名碰撞引发的奇怪问题。对应的缺点就是如果某个头文件有多份拷贝,本方法不能保证他们不被重复包含。当然,相比宏名碰撞引发的"找不到声明"的问题,重复包含更容易被发现并修正。

方式一由语言支持所以移植性好,方式二 可以避免名字冲突

C++模块类

模板是C++支持参数化多态的工具,使用模板可以使用户为类或者函数申明一种一般的模式,使得类中的某些数据成员或者成员函数的参数,返回值取得任意类型。

模板是一种对类型进行参数化的工具,通常有两种形式:函数模板和类模板。

函数模板针对仅参数类型不同的函数,类模板针对仅数据成员和成员函数类型不同的类。

注意:模板的申明或者定义智能在全局,命名空间或者类范围内进行,既不能在局部范围,函数内进行,比如不能在主函数中申请或者定义一个模板。

比如在common/centroid.h文件中

  template <typename PointT, typename Scalar> inline unsigned int

  compute3DCentroid (ConstCloudIterator<PointT> &cloud_iterator,

                     Eigen::Matrix<Scalar, 4, 1> &centroid);

其中类模板和函数模板都是以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中导入的。

点赞(0) 打赏

评论列表 共有 0 条评论

暂无评论

热门产品

php编程基础教程.pptx|php编程培训,php,编程,基础,教程,pptx
php编程基础教程.pptx

历史上的今天:04月20日

ThinkPHP5快速入门基础

ThinkPHP5快速入门基础一、基础快速入门 ( 一 ) :基础本章介绍了 ThinkPHP5 .0 的安装及基本使用 ,并给出了一个最简单的示例带你了解如何开始开发 ,主要包 含 :简介官网下载 omposer安装和更新CGit下载和更新目录结构运行环境入口文件调试模式控制器视图读取数据总结在学习 ThinkPHP5.0 之前 ,如果你还不理解面向对象和命名空间的概念 ,建议首先去PHP手册恶

ThinkPHP5快速入门

ThinkPHP5快速入门目 录零、序言一、基础二、URL和路由三、请求和响应四、数据库五、查询语言六、模型和关联 (1)模型定义 (2)基础操作 (3)读取器和修改器 (4)类型转换和自动完成 (5)查询范围 (6)输入和验证 (7)关联 (8)模型输出七、视图和模板八、调试和日志九、API开发十、命令行工具十一、扩展十二、杂项SessionCookie验证

热门专题

APP开发|app开发_app开发公司_app软件开发_专业app开发_云南app开发公司_app定制_原生app开发定制
APP开发
云南综合高中|云南综合高中
云南综合高中
安徽中源管业|安徽中源管业,安徽中源管业mpp电力管,安徽中源管业cpvc电力管,安徽中源管业pe穿线管,安徽中源管业电力管,安徽中源管业排水管,安徽中源管业通信管,安徽中源管业管材
安徽中源管业
大理科技管理学校|大理科技管理中等职业技术学校,大理市科技管理中等职业技术学校
大理科技管理学校
综合高中|云南综合高中,昆明综合高中,综合高中能考本一吗,综合高中和普通高中的区别,综合高中是什么意思,综合高中能参加全国统一高考吗,综合高中可以考哪些大学,综合高中的学籍是什么
综合高中
中源管业|中源管业,中源管业公司,中源管业有限公司,中源管业电话,中源管业地址,中源管业电力管,中源管业mpp电力管,中源管业cpvc电力管,中源管业pe穿线管
中源管业
安徽开放大学|安徽开放大学报名,安徽开放大学报考,安徽开放大学,什么是安徽开放大学,安徽开放大学学历,安徽开放大学学费,安徽开放大学报名条件,安徽开放大学报名时间,安徽开放大学学历,安徽开放大学专业
安徽开放大学
小程序开发|微信小程序,小程序开发,小程序,小程序制作,微信小程序开发,小程序公司,小程序开发公司,分销,三级分销系统,分销系统
小程序开发

微信小程序

微信扫一扫体验

立即
投稿

微信公众账号

微信扫一扫加关注

发表
评论
返回
顶部