将派生类传递给map c ++

时间:2017-07-26 04:49:23

标签: c++

我想要做的是将经理放入地图,然后调用与每位经理相关的功能。因为我有不同类型的经理,所以我创建了一个类基类:

class iGyroManager {
public:
    iGyroManager() {}
    virtual ~iGyroManager() = default;

    virtual bool preInit() = 0;

    virtual bool init() = 0;

    virtual bool postInit() = 0;

    virtual void update() = 0;

    virtual void cleanup() = 0;
}

非常直接,显然就像一个魅力。

然后我执行以下操作来创建派生类:

class GyroAudioManager : public iGyroManager {
public:
    GyroAudioManager();
    ~GyroAudioManager() override;

    bool preInit() override;

    bool init() override;

    bool postInit override;

    void update() override;

    bool cleanup() override;
}

再一次,简单直接。 cpp是非常基本的,只是声明了裸功能。

然后我创建了一个最终的派生类:

class GyroAppStateManager : iGyroManager {
private:
    std::map<int, iGyroManager&> m_managerMap;

public:
    GyroAppStateManager();
    ~GyroAppStateManager() override;

    bool preInit() override;

    bool init() override;

    bool postInit() override;

    int start();

    void update() override;

    bool registerManager(iGyroManager& manager);

    bool cleanup() override;
}

这似乎有效,但它在registerManager函数中崩溃了:

bool GyroAppStateManager::registerManager(iGyroManager& manager) {
    // Try to insert a derived class into a base class map using what
    // should be working.
    m_managerMap.insert(1, manager);

    return true;
}

在调用函数中:

int start() {
    GyroAudioManager m_audioManager = GyroAudioManager();

    mp_appStateManager->registerManager(m_audioManager);


    /* use mp_appStateManager here, while m_audioManager is alive */
}

除此之外似乎根本不起作用并吐出以下内容:

error: no matching function for call to std::map<int, iGyroManager&>::insert(int, iGyroManager&)

所以我的问题是我做错了什么?正如我上面提到的,我想添加多个不同的管理器类,它们为这个地图派生一个基类,然后能够从中运行某些函数。

实际上有办法吗?

1 个答案:

答案 0 :(得分:2)

您不能拥有标准的参考容器。我仍然在寻找限制的确切措辞,但在此期间你可能想要尝试std::reference_wrapper,或者是一个(智能)指针的容器,它也允许多态性。

实际上,即使value_type是引用,std::pair<key_type, mapped_type>也是mapped_type,它是一种对象类型。所以没关系。

导致错误是因为std::map<Key,Value>::insert的参数是pair<Key,Value>,而不是两个单独的参数。尝试

m_managerMap.insert({1, manager});

但是当你start()返回时,你需要安排引用一个之后不会被销毁的对象。