将指针存储在std :: map中的派生类实例中

时间:2014-11-25 05:56:20

标签: c++ templates segmentation-fault std

我有以下代码。我抽象出来了,我的班级看起来像这样:

#include<iostream>
#include<map>

using namespace std;

template <class K>
class Base {
    private:
        static std::map<std::string, Base*> derived_map;
        //other private data
    public:
        Base(std::string modName) {
            if (derived_map.find(modName) == derived_map.end())
            {
                derived_map.insert(make_pair(modName, this));
            }
        }

};

template <class K> std::map<std::string, Base<K>*> Base<K>::derived_map;

class Derived: public Base<Derived>
{
    public:
    Derived(std::string modname): Base<Derived>(modname)
    {
    }
};


Derived obj("derived1"); // <<< This casuses segfault
int main()
{
}

当我在全局声明Derived obj时,会出现段错误。当我在我的主要内部宣布Derived obj时,它并没有。我无法弄清楚我可能做错了什么。我试图使用std :: map维护我的基类中的派生类指针列表。有线索吗?

1 个答案:

答案 0 :(得分:1)

您有2个具有依赖关系的全局变量:

obj要求Base<Derived>::derived_map正确初始化。

翻译单元的全局初始化以未定义的顺序完成。

您可以使用以下内容解决您的代码:

template <class K>
class Base {
    private:
        static std::map<std::string, Base*>& get_derived_map()
        {
             static std::map<std::string, Base*> derived_map; // initialized the first time
                                                              // get_derived_map is called
             return derived_map;
        }
        //other private data
    public:
        explicit Base(const std::string& modName) {
            get_derived_map().insert(make_pair(modName, this));
        }
};