用于管理应用程序设置的C ++ 11类

时间:2014-05-09 13:59:17

标签: class templates c++11 application-settings

我正在尝试在c ++ 11中实现一个配置管理器类,它将从* .xml文件加载设置。第一个实现(我使用结构代替类只是为了便于测试):

struct ConfigManager
{
    ConfigManager(){}

    void initialize()
    {
        add<CoreSettings>(std::make_unique<CoreSettings>("WhatEver.xml"));
    }

    template <typename T>
    void add(std::unique_ptr<T> settings)
    {
        settings_.insert(std::make_pair(std::type_index(typeid(T)), std::move(settings)));
    }

    template <typename T>
    T& get() const
    {
        auto it = settings_.find(std::type_index(typeid(T)));
        return dynamic_cast<T&>(*it->second);
    }

    void load()
    {
        for (auto& s : settings_)
            s.second->load();
    }

    void save()
    {
        for (auto& s : settings_)
            s.second->save();
    }

    std::map<std::type_index, std::unique_ptr<ISettings>> settings_;
};

它允许我编写如下代码来使用这个类:

ConfigManager confManager;
confManager.initialize();
confManager.load();
auto& coreSettings = confManager.get<CoreSettings>();
coreSettings.windowOptions_.height_ = 800;
confManager.save();

更简单的实现是:

struct ConfigManager : public IConfigManager
{
    ConfigManager()
    {
        set_.insert(&coreSettings_);
    }

    virtual void load() final
    {
        for (auto& s : set_)
            s->load();
    }

    virtual void save() final
    {
        for (auto& s : set_)
            s->save();
    }

    virtual CoreSettings& getCoreSettings() final
    {
        return coreSettings_;
    }

    CoreSettings coreSettings_;
    std::set<ISettings*> set_;
};

但是这样我必须为我将创建的所有类型的设置编写很多getter。

你觉得哪一个更好,为什么?也许这根本不应该怎么做;您的意见表示赞赏。

1 个答案:

答案 0 :(得分:1)

我更喜欢选项#1,正是因为它不需要提前知道所有设置类型。但是,您应该在get()中添加一些错误检查,以便在找不到适当的设置时做出反应(因此it == settings_.end())。