使用 std::string 参数和不可移动/可复制参数构建 std::map

Building a std::map with a std::string parameter and an non-movable/copyable parameter

本文关键字:std 参数 构建 可复制 map string 使用 可移动      更新时间:2023-10-16

我正在尝试构建一个简单的日志系统,但我的概念遇到了问题:

class logger_instance
{
    std::string log_file;
    std::string log_type;
    std::ofstream log;
public:
    logger_instance(std::string log_type) : log_type(log_type), log_file("logs\" + log_type + ".log"), log(log_file)
    {
        operator << ("logger_instance(" + log_type + ") init.n");
    }
    std::string get_log_type() const
    {
        return log_type;
    }
    std::string get_log_file() const
    {
        return log_file;
    }

    logger_instance& operator << (std::string message)
    {
        time_t current_time;
        time(&current_time);
        log << ctime(&current_time);
        log << " : ";
        log << message;
        log << "n";
    }
};
class logger_manager
{
    std::map < std::string, logger_instance > loggers;
public:
    void add_logger(std::string logger)
    {
        auto it = loggers.find(logger);
        if (it == loggers.end())
        {
            loggers.emplace(logger, logger);
        }
    }
    logger_instance& operator[](std::string logger)
    {
        return loggers[logger];
    }
};

编译器:Visual Studio 2013 Update 4

我遇到的问题是 emplace 函数似乎不明白我希望在地图容器中当场构建logger_instance对象。鉴于我并不比编译器聪明,问题出在我的概念上,但我无法找到解决方案。

在地图上放置是一件相当奇怪的事情。我会推荐斯科特·迈耶斯(Scott Meyers)的最新书或看看演讲。这是关于cwuks(斯科特的术语)。

但是要解决您的问题。使用堆。通过将您的logger_instance更改为经理中的unique_ptr。例如:

class logger_manager
{
    std::map < std::string, unique_ptr<logger_instance> > loggers;
public:
    void add_logger(std::string logger)
    {
        auto it = loggers.find(logger);
        if (it == loggers.end())
        {
            loggers.emplace(logger, make_unique<logger_instance>(logger));
        }
    }
    logger_instance& operator[](std::string logger)
    {
        return *loggers[logger];
    }
};