我知道如何为不包含类的dll使用显式链接但是如何链接dll包含类,例如:
class math{
public:
int sum(int,int);
};
加载它:
typedef int(*func)(int,int);
int main{
HINSTANCE hDLL; // Handle to DLL
hDLL = LoadLibrary("math.dll");
func add=(func)GetProcAddress(hDLL, "sum");
add(4,5);
return 0;
}
如果我这样做它停止工作并退出程序,如果我删除它工作的类
答案 0 :(得分:2)
GetProcAddress可以从DLL中加载导出的符号,前提是您使用正确的名称调用它。
在您的情况下,该功能首先不会导出。如果是的话,它肯定不会被称为“总和”,而是一些带有20-40个字符的乱码。
对于使用带有C ++代码的DLL,您需要完全删除GetProcAddress方法,并且只依赖于映射名称的implib。
为此您将__declspec(dllexport)添加到类中(最好在客户端使用dllimport),并将您的DLL项目添加为项目引用。或者,将随DLL一起创建的.lib添加到客户端项目中。
答案 1 :(得分:2)
C ++编译器使用name mangling来唯一地区分程序中的标识符。此修改导致名称与您在程序中使用的普通标识符明显不同。因此使用GetProcAddress
对于访问驻留在DLL中的C ++编写的代码通常是不切实际的。相反,我建议使用__declspec(dllexport)
和__declspec(dllimport)
轻松访问驻留在DLL中的代码。
在DLL的项目中,您需要添加一个名为“EXPORT_CLASSES”的预处理器定义或DLL独有的名称。这将由您的DLL和程序使用,以确定特定声明是由DLL导出还是由程序导入。
dllstuff.h
#ifdef EXPORT_CLASSES
#define IMPORT_EXPORT __declspec(dllexport)
#else
#define IMPORT_EXPORT __declspec(dllimport)
#endif
然后,您将更改math
的类声明以使用它。编译DLL时,IMPORT_EXPORT将等于__declspec(dllexport)
,并将指示编译器和链接器应该公开该类的定义(即通过DLL的导出表)。
mathclass.h
#include "dllstuff.h"
class IMPORT_EXPORT math
{
public:
int sum(int, int);
};
现在,只要您想使用数学课,您在主应用程序中所要做的就是包含mathclass.h
。您现在可以实例化math
的实例并访问它的成员函数。
#include "mathclass.h"
int main()
{
math m;
int result = m.sum(1, 2);
}
这当然只是该过程的基本描述。网上有很多文章(包括SO),提供更详细的信息。