我正在编写一个实用程序类库,其中许多都是单例。我已经使用继承来实现它们:
template <class T>
class Singleton {
public:
T& getInstance() {
if(m_instance == 0) {
m_instance = new T;
}
return m_instance;
}
private:
static T* m_instance;
};
class SomeClass : public Singleton<SomeClass> {
public:
SomeClass() {}
virtual ~SomeClass() {}
void doSomething() {;}
};
显然这是一个简单的例子,而不是一个实际的类。无论如何,我发现使用如下代码:
SomeClass::getInstance().doSomething();
将创建多个 SomeClass 实例。我认为这可能是因为它在我的库(.a)文件之外以及内部使用。例如,我正在使用一个不是我自己编写的 UI 库,它是单独编译的,并且我正在对其进行添加。其中一些添加使用了单例,这些单例也在我的 .a 库中使用。
是单独编译造成的吗?还有别的事吗?
我设法解决这个问题的唯一方法是在我的 main.cpp 文件中创建一个全局对象,我用我需要的任何单例来初始化它。然后所有代码都通过以下调用访问这个公共全局对象:
GlobalObject::getSomeClass().doSomething()
我讨厌每次创建另一个单例时都必须向该对象添加额外的方法。另外,使用第一种访问方法,语法似乎更清晰、更熟悉:
SomeClass::getInstance().doSomething();
如果您有任何想法、意见等,请告诉我。
Thanks.
您的问题是您的模板将在多个编译单元中实例化,因为它是完全内联的。因此,在每个使用模板的编译单元中,您最终将创建一个单例(每个编译单元)。您需要的是强制全局链接,以便所有编译单元引用相同的模板实例化。即将推出的 C++ 标准将通过以下方式支持此功能外部模板 http://en.wikipedia.org/wiki/C++0x#Extern_template。您现在可以做的是在项目中禁用自动实例化并手动实例化您显式使用的模板。这样,当您在任何编译单元中使用模板时,您将生成对实现的未知引用,然后可以由进行显式实例化的(一个)编译单元中的链接器来满足该引用。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)