我有一个基类(QIndicator
),我想在DLL中实现派生类。 Visual Studio 2012中用于示例派生类的DLL项目具有以下代码:
基类的头文件
#ifndef _DLL_COMMON_INDICATOR_
#define _DLL_COMMON_INDICATOR_
// define the DLL storage specifier macro
#if defined DLL_EXPORT
#define DECLDIR __declspec(dllexport)
#else
#define DECLDIR __declspec(dllimport)
#endif
class QIndicator
{
private:
int x;
int y;
};
extern "C"
{
// declare the factory function for exporting a pointer to QIndicator
DECLDIR QIndicator * __stdcall getIndicatorPtr(void);
}
#endif
派生类的源文件
#define DLL_EXPORT
#include "indicator.h"
class QIndicatorDer : public QIndicator
{
public:
QIndicatorDer (void) : QIndicator(){};
~QIndicatorDer (void){};
private:
// list of QIndicatorDer parameters
int x2;
int y2;
};
extern "C"
{
DECLDIR QIndicator * __stdcall getIndicatorPtr(void)
{
return new QIndicatorDer();
};
}
我遇到的问题是,在成功构建后,生成的DLL文件不包含导出的getIndicatorPtr
函数(如DependencyWalker所示)。我检查了dllexport
关键字是否正确传播到getIndicatorPtr
的声明中,并确实如此。
另一个有趣的问题是,我在几个月前创建的另一个DLL项目中已经有了这样的另一个派生类。这个较旧的项目基本相同,一切都很好。我检查了旧项目和当前项目的所有属性,它们看起来完全相同。所以我没有想法,为什么我不能导出getIndicatorPtr
。
非常感谢任何帮助, 丹尼尔
答案 0 :(得分:2)
那是因为它没有被导出。为什么呢?
__declspec
说明符只能放在函数的声明中,而不能放在它的定义中。另外,请避免使用#define DLL_EXPORT
之类的内容。预处理程序定义应在项目属性(MSVC)或命令行选项(例如GCC中的-D
)中定义。
看看你的代码:
标题强>
extern "C"
{
DECLDIR QIndicator * __stdcall getIndicatorPtr(void);
}
当编译器解析此标头时,会将DECLDIR
视为dllimport
(因为您在DLL_EXPORT
中定义了.cpp
)。然后在.cpp
中,它突然显示为dllexport
。使用哪一个?第一个。
所以,留下你的标题(没关系),但改变你的来源:
//#define DLL_EXPORT -> remove this!
#include "indicator.h"
class QIndicatorDer : public QIndicator
{
//...
};
extern "C"
{
/* DECLDIR -> and this! */ QIndicator * __stdcall getIndicatorPtr(void)
{
return new QIndicatorDer();
};
}
然后,转到项目属性(我假设您使用Visual Studio),然后C/C++
- > Preprocessor
- > Preprocessor Definitions
并添加DLL_EXPORT=1
。
这应该有效。