我有一个大型项目,旨在控制和测试硬件。
有 4 个 设备 控制 类 (用于 干涉 仪、 压 电 电机、 PXI 系统 和 纳米 定位 控制器)。
我创建了一个名为 MainIO 的"主"类,它存储上述每个类的实例,以便在 IO 范围内执行操作(即移动电机和检查干涉仪)。MainIO 头文件包括 4 个控件类头。
然后我有一个单独的"全局"hpp/cpp,其中包含全局变量、转换、ini 文件操作等。这是用操作类型的命名空间布置的,而不是创建一个类,即 GCONV::someFunction();
和GMAIN::controllerModel;
我需要所有 4 个控件类才能访问转换和其他全局操作。我曾经让它们都包含 global.hpp,但我已经更改了一些东西(我想不出它会是什么!)现在似乎我不能在我的任何控制类 hpp 或 cpp 中包含 global.hpp 而不会收到链接器错误 -
global.obj:-1: error: LNK2005: "class QString GMAIN::controllerModel" (?controllerModel@GMAIN@@3VQString@@A) already defined in controllers.obj
绝对确定我做了一些愚蠢的事情,解决方案正盯着我的脸,但它已经到了我感到非常沮丧的阶段,以至于我看不到树木的木头。
我已经发现了我做错了什么,虽然它非常简单,但我花了一段时间才找到相关的文档来发现我的错误,所以我会回答我自己的问题,希望给别人一个更轻松的时间。
事实证明,在global.hpp中,我在命名空间中声明了变量,如下所示:
namespace GMAIN {
QString controllerModel;
}
从本质上讲,这意味着每个包含 global.hpp 的文件都将包含自己的QString controllerModel
定义,从而引发链接器错误。每个控件类都有自己的同一命名变量定义,这违反了一个定义规则。
为了解决这个问题,QString controllerModel需要被extern'ed。extern 关键字允许在多个位置声明变量,同时只有一个定义(因此不会违反规则)。
所以工作代码现在是:
//in global.hpp
namespace GMAIN {
extern QString controllerModel; //declaration - this is called for each `#include global.hpp`
}
//in global.cpp
namespace GMAIN {
QString controllerModel; //definition - only called once as .cpp is never included
}
您是否正在定义控制器模型,而您应该只声明它?http://www.cprogramming.com/declare_vs_define.html
你应该导出你的dll。使用 __declspec(dllexport)
.可以将__declspec(dllexport)
作为宏包含在头文件中,并将宏放在每个成员函数的开头。
例如:在Header.h
文件中包括
#define MYMACRO __declspec(dllexport);
在你的课堂上
class classname
{
public:
MYMACRO void MYFUNCTION();
MYMACRO void MYFUNCTION2();
};