赞助

VS2015 创建C++动态库及使用

 

转载:https://blog.csdn.net/w_x_myself/article/details/82252646

1.dll的特点

代码复用是提高软件开发效率的重要途径。一般而言,只要某部分代码具有通用性,就可将它构造成相对独立的功能模块并在之后的项目中重复使用。比较常见的例子是各种应用程序框架,ATL、MFC等,它们都以源代码的形式发布。由于这种复用是“源码级别”的,源代码完全暴露给了程序员,因而称之为“白盒复用”。“白盒复用”的缺点比较多,总结起来有4点。 
   暴露了源代码;

   多份拷贝,造成存储浪费; 

   容易与程序员的“普通”代码发生命名冲突; 

   更新功能模块比较困难,不利于问题的模块化实现; 
实际上,以上4点概括起来就是“暴露的源代码”造成“代码严重耦合”。为了弥补这些不足,就提出了“二进制级别”的代码复用。使用二进制级别的代码复用一定程度上隐藏了源代码,对于缓解代码耦合现象起到了一定的作用。这样的复用被称为“黑盒复用”。 

说明:实现“黑盒复用”的途径不只dll一种,静态链接库甚至更高级的COM组件都是。

2.VS创建新一个空的解决方案(一个解决方案下可以有很多project)

2.创建dll

文件------>新建------>项目------>Win32控制台应用程序------>

 选择dll -- 勾选导出符号 -- 不勾选预编译头文件

删除stdafx.h 、stdafx.cpp、targetver.h、dllmain.cpp,把MyDll.h修改成dllexport.dll。修改MyDll.cpp中#include "stdafx.h" #include "MyDll.h"改为 "dllexport.h"

 

如果生产dll和使用dll的工程在一个解决方案中,我们可以指定dll输出目录

 

 $(SolutionDir)  ---  解决方案目录

 $(Platform)       ---- 平台目录(x86/x64)

 $(Configuration) --- 编译模式(Debug/Release)

因为dll库是函数的实现,lib里面是函数的声明,我们也指定他的输出路径

 这是我们编译工程:

这时在解决方案目录下生成bin和lib目录

3.创建useDll工程

使用dll

导入头文件  指定导入

 

在运行之前我们要指定UseDll工程的exe的输出目录

 

 运行结果:

通过配置工程属性来使用dll库

工程—属性—配置属性—链接器—常规—附加库目录:加上lib文件存放目录。 
然后添加工程引用的lib文件名:工程—属性—配置属性—链接器—输入—附加依赖项:加上lib文件名。

 

 

 

 

显式调用dll:获取dll库的路径,无需配置环境,无法进行隐式链接

 

调用:

#include "stdafx.h"
#include <iostream>
#include <Windows.h>
#include <Shlwapi.h>// 使用PathRemoveFileSpec函数
using namespace std;
#pragma comment(lib, "shlwapi.lib") //这个库也要有,不然会报链接错误

typedef int(*MyAdd)(int a,int b);
typedef int(*MySub)(int i,int j);

int main()
{
    TCHAR  ModulePath[MAX_PATH] = { 0 };
    GetModuleFileName(NULL,ModulePath,MAX_PATH);
    ::PathRemoveFileSpec(ModulePath);//C:\\TestDemo\\Debug

    wstring dllpath = ModulePath;
    dllpath += L"\\FunDll.dll";

    HMODULE hModule = LoadLibrary(dllpath.c_str());

    if (hModule)
    {
        MyAdd func = (MyAdd)GetProcAddress(hModule, "Add");//显式调用dll中的Add

        cout << func(1, 5) << endl;

        MySub funs = (MySub)GetProcAddress(hModule,"Sub');//显式调用dll中的Sub

        cout << funs(5,3) <<endl;
    }

    cout << fnMyDll() << endl;//调用dll中的函数

    FreeLibrary(hModule);
    return 0;
}

 demo

posted @ 2019-08-26 21:24  车臣  阅读(8403)  评论(0编辑  收藏  举报