h、cpp和hpp头文件之间使用区别

hpp,其实质就是将.cpp的实现代码混入.h头文件当中,定义与实现都包含在同一文件,则该类的调用者只需要include该hpp文件即可,无需再将cpp加入到project中进行编译。而实现代码将直接编译到调用者的obj文件中,不再生成单独的obj,采用hpp将大幅度减少调用 project中的cpp文件数与编译次数,也不用再发布烦人的lib与dll,因此非常适合用来编写公用的开源库。

hpp的优点不少,但是编写中有以下几点要注意:

1、是Header Plus Plus 的简写。

2、与*.h类似,hpp是C++程序头文件 。

3、是VCL专用的头文件,已预编译。

4、是一般模板类的头文件。

5、一般来说,.h里面只有声明,没有实现,而.hpp里声明实现都有,后者可以减少.cpp的数量。

6、.h里面可以有using namespace std,而.hpp里则无。

7、不可包含全局对象和全局函数。

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

8、类之间不可循环调用。

在.h和.cpp的场景中,当两个类或者多个类之间有循环调用关系时,只要预先在头文件做被调用类的声明即可,如下:

class B;class A{
public:void someMethod(B b);
};class B{
public :void someMethod(A a);
};

在hpp场景中,由于定义与实现都已经存在于一个文件,调用者必需明确知道被调用者的所有定义,而不能等到cpp中去编译。因此hpp中必须整理类之间调用关系,不可产生循环调用。同理,对于当两个类A和B分别定义在各自的hpp文件中,形如以下的循环调用也将导致编译错误:

//a.hpp
#include "b.hpp"
class A{
public :void someMethod(B b);
};//b.hpp
#include "a.hpp"
class B{
public :void someMethod(A a);
};

9、不可使用静态成员。

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

class A{
public:const static int intValue = 123;
};

由于静态成员的使用是很常见的场景,无法强制清除,因此可以考虑以下几种方式(以下示例均为同一类中方法)

1.类中仅有一个静态成员时,且仅有一个调用者时,可以通过局域静态变量模拟

//方法模拟获取静态成员
someType getMember()
{static someTypevalue(xxx);//作用域内静态变量return value;
}

2.类中有多个方法需要调用静态成员,而且可能存在多个静态成员时,可以将每个静态成员封装一个模拟方法,供其他方法调用。

someType getMemberA()
{static someTypevalue(xxx);//作用域内静态变量return value;
}someType getMemberB()
{static someTypevalue(xxx);//作用域内静态变量return value;
}void accessMemberA()
{someType member = getMemberA();//获取静态成员
};//获取两个静态成员void accessStaticMember()
{someType a  = getMemberA();//获取静态成员someType b = getMemberB();
};

3.第二种方法对于大部分情况是通用的,但是当所需的静态成员过多时,编写封装方法的工作量将非常巨大,在此种情况下,建议使用Singleton模式,将被调用类定义成普通类,然后使用Singleton将其变为全局唯一的对象进行调用。

如原h+cpp下的定义如下:

class A{
public :type getMember(){return member;}static type member;//静态成员
}

采用singleton方式,实现代码可能如下(singleton实现请自行查阅相关文档)

//实际实现类
class Aprovider{
public :type getMember(){return member;}type member;//变为普通成员
}//提供给调用者的接口类
class A{
public :type getMember(){return Singleton<AProvider >::getInstance()->getMember();}
}   

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

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

相关文章

未声明spire。它可能因保护级别而不可访问_信息系统安全:访问控制技术概述...

1.访问控制基本概念身份认证技术解决了识别“用户是谁”的问题&#xff0c;那么认证通过的用户是不是可以无条件地使用所有资源呢&#xff1f;答案是否定的。访问控制(Access Control)技术就是用来管理用户对系统资源的访问。访问控制是国际标准ISO7498-2中的五项安全服务之一&…

c++反汇编与逆向分析技术揭秘_C++反汇编与逆向分析技术揭秘

一、单类继承在父类中声明为私有的成员&#xff0c;子类对象无法直接访问&#xff0c;但是在子类对象的内存结构中&#xff0c;父类私有的成员数据依然存在。C语法规定的访问限制仅限于编译层面&#xff0c;在编译过程中进行语法检查&#xff0c;因此访问控制不会影响对象的内存…

std::atomic原子操作

第十一节std::atomic原子操作_HITXJ的博客-CSDN博客_std::atomic用法

mysql 列级权限授予用户_mysql 用户及权限管理 小结

MySQL 默认有个root用户&#xff0c;但是这个用户权限太大&#xff0c;一般只在管理数据库时候才用。如果在项目中要连接 MySQL 数据库&#xff0c;则建议新建一个权限较小的用户来连接。在 MySQL 命令行模式下输入如下命令可以为 MySQL 创建一个新用户&#xff1a;新用户创建完…

python if name main 的作用_Python中if __name__ == __main__: 的作用

在很多python脚本中在最后的部分会执行一个判断语句if __name__ "__main__:"&#xff0c;之后还可能会有一些执行语句。那添加这个判断的目的何在&#xff1f; 在python编译器读取源文件的时候会执行它找到的所有代码&#xff0c;而在执行之前会根据当前运行的模块是…

php与mysql列表_PHP+Mysql+jQuery实现的查询和列表框选择

本篇文章主要介绍PHPMysqljQuery实现的查询和列表框选择&#xff0c;感兴趣的朋友参考下&#xff0c;希望对大家有所帮助。本文讲解如何通过ajax查询mysql数据&#xff0c;并将返回的数据显示在待选列表中&#xff0c;再通过选择最终将选项加入到已选区&#xff0c;可以用在许多…

range函数python2和3区别_range函数python2和3区别

range函数是一个用来创建算数级数序列的通用函数&#xff0c;返回一个[start, start step, start 2 * step, ...]结构的整数序列&#xff1b;py2中的range()函数用法&#xff1a;&#xff08;推荐学习&#xff1a;Python视频教程&#xff09; range()返回的是一个列表>>&…

Unity SRP自定义渲染管线 -- 2.Custom Shaders

本章将接着上一篇文章&#xff0c;在初步实现一个渲染管线后来创建自定义的shader。上一篇文章的链接 https://blog.csdn.net/yinfourever/article/details/90516602。在本章中&#xff0c;将完成以下内容&#xff1a; 写一个HLSL Shader定义constant buffer&#xff08;常量缓…

tcp 三次握手与四次挥手_TCP三次握手与四次挥手详解

TCP报文结构源端口和目的端口&#xff1a;各占2个字节&#xff0c;分别写入源端口号和目的端口号。序号&#xff1a;占4个字节。序号使用mod运算。TCP是面向字节流的&#xff0c;在一个TCP连接中传送的字节流中的每一个字节都按顺序编号。故该字段也叫做“报文段序号”。确认序…

网关和路由器的区别_5G工业路由器与5G DTU的区别介绍详解

5G工业路由器和5G DTU都是实现无线网络数据传输功能&#xff0c;而两者间的区别主要从使用方法、外观接口以及应用环境等方面区分&#xff0c;今天给大家介绍5G工业路由器和5G DTU的一些不同点。使用方法的不同:5G工业路由器&#xff1a;5G路由器可对以太网、现场总线通信协议进…

7628刷breed_自制各类路由原厂直刷Breed的文件,无需修改mac无需重刷无线

本帖最后由 showme99 于 2017-3-25 16:35 编辑在原厂页面直接选择相应的刷机文件刷机&#xff0c;文件很小256K&#xff0c;大约十秒左右就自动进入Breed后直接刷入dd-wrt,opentwrt,gargoyle等固件即可。无需在Breed里设置MAC地址&#xff0c;也无需刷入ART无线文件&#xff0c…

c语言获取系统剩余内存_C语言编程中的“堆”和“栈”七大不同之处

更多精彩&#xff0c;请点击上方蓝字关注我们&#xff01;对于编程初学者来说会接触到一些难以理解的名称&#xff0c;比如堆(heap)、栈(stack)、堆栈(stack)等。初学开发过程中往往让人混淆不清。今天我们来谈谈堆和栈的具体区别&#xff0c;来帮助初学者理清思路。堆和栈的区…

sql between包括两端吗_SQL大全

作者&#xff1a;静默虚空排版&#xff1a;MarkerHub原文&#xff1a;https://juejin.im/post/5c7e524af265da2d914db18f本文针对关系型数据库的一般语法。限于篇幅&#xff0c;本文侧重说明用法&#xff0c;不会展开讲解特性、原理。一、基本概念数据库术语数据库(database) -…

date oracle 显示毫秒_Oracle中根据Date型转换成Java对应的long型毫秒数

在Java开发中&#xff0c;很多时候我们为了方便会直接使用long型来保存时间&#xff0c;可以通过System.currentTimeMillis()或者是java.util.Date.getTime()来获取&#xff1b;取值为当前日期时间与1970-01-01相差的毫秒数&#xff1b;但是在Oracle里面&#xff0c;默认没有直…

python交互模式什么意思_Python中的交互模式是什么

让开发者能快速学习、测试 Python 的各种功能&#xff0c;Python 提供的“python”命令不仅能用于运行 Python 程序&#xff0c;也可作为一个交互式解释器一一开发者逐行输入 Python 代码&#xff0c;它逐行解释执行。 当输入“python”命令时&#xff0c;可以看到如下输出结果…

linux下centos安装mysql数据库_Linux CentOS 下的MySQL数据库安装与配置-阿里云开发者社区...

安装mysqlyum -y install mysqlyum -y install mysql-serveryum -y install php-mysqlyum -y install mysql-devel2.配置MySQL[rootsample ~]#vim /etc/my.cnf ← 编辑MySQL的配置文件[mysqld]datadir/var/lib/mysqlsocket/var/lib/mysql/mysql.sock# Default to using old pas…

idea创建springboot项目+mybatis_Spring Boot + MyBatis 多模块项目搭建教程

Java后端&#xff0c;选择“”优质文章&#xff0c;及时送达作者 | 枫本非凡链接 | cnblogs.com/orzlin/p/9717399.html上篇 | IDEA 远程一键部署 Spring Boot 到 Docker一、前言最近公司项目准备开始重构&#xff0c;框架选定为SpringBootMybatis&#xff0c;本篇主要记录了在…

下载nodejs的mysql安装包下载安装_Node.js安装 下载

1、安装Node.jshttps://nodejs.org/en/安装步骤&#xff1a;点击安装包按提示进行安装Node.js 安装配置本章节我们将向大家介绍在 Windows 和 Linux 上安装 Node.js 的方法。本安装教程以 Node.js v4.4.3 LTS(长期支持版本)版本为例。你可以根据不同平台系统选择你需要的 Node.…

redistemplate注入为null_Windows DLL 注入技术

Windows DLL 注入技术 本文主要介绍四种常见的 Windows DLL 注入技术。分别为全局钩子、远线程钩子、突破 SESSION 0 隔离的远线程注入和 APC 注入。全局钩子注入Windows 中大部分应用是基于 Windows 的消息机制&#xff0c;Windows提供截获这些消息的钩子函数。根据钩子作用的…

nginx location 正则表达式匹配多个地址_就是要让你搞懂Nginx,这篇就够了!

Nginx 是一个高性能的 HTTP 和反向代理服务器&#xff0c;特点是占用内存少&#xff0c;并发能力强&#xff0c;事实上 Nginx 的并发能力确实在同类型的网页服务器中表现较好。Nginx 专为性能优化而开发&#xff0c;性能是其最重要的要求&#xff0c;十分注重效率&#xff0c;有…