概要

设想这样一个场景:我有一个类FunClass,它的声明位于FunClass.h,并且在FunClass.h中,我还引用了secret.h.

现在我需要把FunClass导出成DLL文件供别人二次开发. 这时我需要给别人以下文件:

  • FunClass.h
  • FunClass.lib
  • FunClass.dll
  • secret.h

然而我并不想把secret.h给别人!这个问题可以用一个虚类Fun(名字瞎起的,不重要,Java的风格是IFunClass,然而我们是C++) 来解决。

一个简单的例子

假设我的FunClass有一个方法void A(),和一个依赖secret.h的成员Secret M。那么虚类应当这样写(请为这个虚类新建一个头文件):

////////////////////
//// fun.h
////////////////////
// 请在导出DLL的工程里加上 FUN_EXPORT 预编译指令
#ifndef FUN_EXPORT
#define FUN_API __declspec(dllexport)
#else
#define FUN_API __declspec(dllimport)
#endif // #include something else
// 注意头文件中没有包含 secret.h class FUN_API Fun{
public:
Fun(){};
virtual ~Fun(){}; virtual A() = 0;
// 注意这里没有定义 Secret M
}
FUN_API Fun* createFun();

然后Fun的实现写在Fun.cpp中:

////////////////////
//// fun.cpp
//////////////////// #include "Fun.h"
#include "secret.h"
// #include something else // FunClass 继承自 Fun
class FunClass : public Fun{
public:
FunClass(){};
virtual ~Fun(){}; virtual A();
private:
secret M;
} Fun* createFun(){
return new FunClass();
}; void FunClass::A(){
// A的实现
}

好了!这样就OK了!编译之后会得到Fun.libFun.dll,再加上Fun.h,只需要这三个文件,就能把DLL文件用在其他工程了,下面这段代码是测试:

////////////////////
//// test.cpp
//////////////////// #include "Fun.h" int main(){
Fun* fun = createFun(); // 虽然看起来比较奇怪,但是为了隐藏 secret.h ,忍了!
fun->A(); // fun 指向一个[FunClass类的实例](用F替代吧),
delete fun; // 由于Fun的析构函数是虚函数,所以fun在析构时会自动调用F的析构函数。
}


本作品采用知识共享署名-非商业性使用 4.0 国际许可协议进行许可。

利用虚函数减少导出DLL的头文件依赖的更多相关文章

  1. C++入门经典-例8.7-多态,利用虚函数实现动态绑定

    1:多态性是面向对象程序设计的一个重要特征,利用多态性可以设计和实现一个易于扩展的系统.在C++语言中,多态是指具有不同功能的函数可以用同一个函数名,这样就可以用一个函数名调用不同内容的函数,发出同样 ...

  2. 用javah 导出类的头文件, 常见的错误及正确的使用方法

    ******************************************************************************** 用javah 导出类的头文件, 常见的 ...

  3. [转] 关于c++的头文件依赖

    http://www.cnblogs.com/yvesliao/p/3938730.html PS: 使用单向依赖 正在看google c++编程规范,里面对头文件依赖是这么说的: 1 2 3 4 5 ...

  4. 关于c++的头文件依赖

    正在看google c++编程规范,里面对头文件依赖是这么说的: 使用前置声明(forward declarations)尽量减少.h文件中#include的数量. 当一个头文件被包含的同时也引入了一 ...

  5. Makefile自动生成头文件依赖

    前言 Makefile自动生成头文件依赖是很常用的功能,本文的目的是想尽量详细说明其中的原理和过程. Makefile模板 首先给出一个本人在小项目中常用的Makefile模板,支持自动生成头文件依赖 ...

  6. Makefile中自动生成头文件依赖

    为什么需要自动生成头文件依赖? 编译单个源文件时,需要获取文件中包含的头文件的信息,但是一般的Makefile不会在规则中明确写明文件依赖的头文件,所以单独修改头文件后,不会导致包含头文件的源文件重新 ...

  7. CPLUSPLUS 获得 一个源文件的头文件依赖。即该文件所需要的所有头文件

    核心命令:gcc -M *.h.*.cpp 转: 自动处理头文件的依赖关系 http://blog.csdn.net/su_ocean16/article/details/5374696 现在我们的M ...

  8. C++学习之路—多态性与虚函数(一)利用虚函数实现动态多态性

    (根据<C++程序设计>(谭浩强)整理,整理者:华科小涛,@http://www.cnblogs.com/hust-ghtao转载请注明) 多态性是面向对象程序设计的一个重要特征.顾名思义 ...

  9. Class-dump 安装和使用记录(导出应用的头文件)

    class-dump算是逆向工程中一个入门级的工具,可以很方便的导出程序头文件,可以轻松的了解程序结构方便逆向.安装包下载地址:http://stevenygard.com/projects/clas ...

随机推荐

  1. Python之路2Day(基础深入)

    一,整数 1.int型 具有的功能: class int(object): (1).返回表示该数字的时占用的最少位数 def bit_length(self): 例: >>> bin ...

  2. 学习Machine Leaning In Action(四):逻辑回归

    第一眼看到逻辑回归(Logistic Regression)这个词时,脑海中没有任何概念,读了几页后,发现这非常类似于神经网络中单个神经元的分类方法. 书中逻辑回归的思想是用一个超平面将数据集分为两部 ...

  3. cf 323A A. Black-and-White Cube 立体构造 不知道为什么当k为奇数时构造不出来 挺有趣的题目吧

    A. Black-and-White Cube time limit per test 1 second memory limit per test 256 megabytes input stand ...

  4. etcd使用之ttl不准确问题

    问题现象 部署有一个etcd集群,分别是10.8.65.106,10.8.65.107和10.8.65.108. 然后我使用etcdctl为一个值设置ttl,然后通过watch观察,发现失效时间不准确 ...

  5. 使用 IDEA 创建 Maven Web 项目 (一)- 使用IEAD创建Maven项目

    创建IDEA项目 单击 Create New Project 按钮,弹出 New Project 对话框. 选择 Maven 选项,单击 Next 按钮. 输入 GroupId.ArtifactId. ...

  6. CSS3样式linear-gradient的使用

    linear-gradient linear-gradient是CSS3中新增的样式,主要用于颜色的渐变效果.MDN地址 linear-gradient在不同内核下使用方式不同,详细内容可参考w3cp ...

  7. 结构-行为-样式-Jquery实现延迟加载特效(数据缓冲特效)

    最近在做一个地产项目的过程中,原来用的延迟加载的插件在IE下会使浏览器突然缩小,这个让客户很不满意,于是就考虑到兼容性的问题决定自己写一个插件.思路:定义一个代码块,手动加载到页面,然后手动删除.   ...

  8. 7 -- Spring的基本用法 -- 10...

    7.10 高级依赖关系配置 组件与组件之间的耦合,采用依赖注入管理:但基本类型的成员变量值,应直接在代码中设置. Spring支持将任意方法的返回值.类或对象的Field值.其他Bean的getter ...

  9. R和python连接SQL sever 数据库操作

    在R的使用中,为了方便提取数据, 我们经常要进行数据库进行操作,接下来我们尝试使用R进行连接数据. 这里我们使用R中的RODBC进行操作, 首先,我们需要先配置ODBC资源管理器 通过任务管理器或者w ...

  10. python爬虫---python3.5---eclipse

    解析中文会出现\xbe\c8\90\hd........ 这个和你的编码选择有关.如果是解析成html,则需 fout = open('output.html', 'w',encoding='utf- ...