模板类函数中的静态变量被全局静态变量

时间:2016-11-09 11:34:02

标签: c++ visual-studio-2015 static

我在模板类函数中有一个静态变量,如下所示:

template<class T>
struct builder 
{
    static T* buildOrGet() 
    { 
        static T* built = nullptr;
        if(built == nullptr) built = new T;
        return built;
    }
};

以及代码中的其他地方带有构造函数的全局变量。

static SomeClass global_var;

起初我不知道发生了什么,但built变量在程序的某一点无缘无故地被破坏了。然后,我在&built上的visual studio中添加了一个4字节的数据断点,以查看谁在built = new T;之后压碎了它的内存,实际上它是在初始化{{1}的成员时在C ++动态初始化程序期间在global_var构造函数中。 代码在一个DLL中,由exe自动加载,具体取决于它。 它就像SomeClass内存重叠global_var内存,这非常奇怪。

我真的不明白为什么以及如何发生这种情况除了Visual Studio 2015中的错误,你能帮助我吗?

1 个答案:

答案 0 :(得分:0)

我找到了解决方案: 实际上我在我的dll的不同翻译单元中有多个global_var具有相同的名称,但它们没有相同的类型(假设另一个具有int类型)。

在这种情况下(这对我来说很奇怪,因为它们是'静态'),链接器只保留一个并为所有变量使用相同的内存(它保存在int一个)。

这就是出错的地方......我仍然为上面提到的global_var调用了SomeClass构造函数,但它的内存不是sizeof(SomeClass),而是sizeof(int)这是溢出发生的地方

对我来说这是一个错误,因为链接器应该注意到我这些具有不同类型的同名变量或/并且应该避免在与构造的内存不匹配的变量上调用构造函数。

解决方案是:永远不要在不同的翻译单元中声明两个具有相同名称的静态变量,只有一个会存活,你无法猜出哪一个。