c++ - 我怎样才能创建我的单例常量实例?

标签 c++ singleton constants logging

我正在尝试为 Ogre(一种开源 3D 引擎)的标准日志记录类制作一个包装器。我希望它具有与 std::cerr 相同的语法, 在 Linux 上运行时也会输出到 cerr。这是我拥有的:

#ifndef _LOGGER_H_
#define _LOGGER_H_

#ifndef _XSTRING_
    #include <xstring>
#endif

#ifndef __LogManager_H__
    #include "OgreLogManager.h"
#endif

class Logger
{

public:

    static Logger* m_Instance;
    static Logger* getInstance() { return m_Instance; }
    static const Logger& getInstanceConst() { return *m_Instance; }

    Logger& operator << (const std::string& a_Message)
    {
        m_Log.append(a_Message);
        _CheckNewLine();
        return *m_Instance;
    }

    Logger& operator << (const char* a_Message)
    {
    m_Log += a_Message;
    _CheckNewLine();
    return *m_Instance;
}

private:

    std::string m_Log;

    Logger() 
    {
        m_Log = "";
    }

    void _CheckNewLine()
    {
        if (m_Log.at(m_Log.size() - 1) == '\n')
        {   
            Ogre::LogManager::getSingleton().logMessage(m_Log);

#if OGRE_PLATFORM != PLATFORM_WIN32 && OGRE_PLATFORM != OGRE_PLATFORM_WIN32

            std::cerr << m_Log;

#endif

            m_Log.clear();
        }
    }
};

#endif

现在,这工作正常,并且这个单例在 .cpp 中实例化:

#include "logger.h"

Logger* Logger::m_Instance = new Logger(); 

当我想在多个 header 中使用单例时,问题就来了。我在 game3d.h 中实例化它,它包含在几乎所有标题中,如下所示:

Logger awesomelogger = Logger::getInstance();

不幸的是,这会产生多个有关 header 尝试重新声明 awesomelogger 的错误.

我想让它成为一个 const,这会使它消失,但会引入新的错误。这是我尝试过的:

friend Logger& operator << (const Logger& a_Logger, const std::string& a_Message)
{
    a_Logger.m_Log.append(a_Message);
    a_Logger._CheckNewLine();
    return *m_Instance;
}

我的问题是:如何使此类常量的实例或如何重写此类但仍然能够做到 awesomelogger << "output" << s_Stuff << "\n";

最佳答案

与您的问题无关,但请注意 _LOGGER_H___LogManager_H__ 等名称在 C++ 中是保留的 - 您不能在自己的代码中使用它们。如果您不理解有关名称开头的下划线(或任何地方的双下划线)的规则,请不要使用它们。

现在,关于您的问题,记录器显然不是常量。提供对单例的访问的经典方法是对此的一些变体:

static Logger* getInstance() { 
    static Logger logger;
    return & logger; 
}

关于c++ - 我怎样才能创建我的单例常量实例?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1150698/

相关文章:

Objective-C 替代使用 ApplicationDelegate 或单例来传递数据

c++ - Const 丢弃限定符 : C++

case - Elixir:在 case 语句中使用变量

c++ - cin 一行中未定义的坐标数

java - 异常 JNI (Ljava/lang/String;)Ljava/lang/String;

java - 具有静态内部类和双重检查锁定的单例

常量的另一个名字

c++ - "Default member initializer needed within definition of enclosing class outside of member functions"- 我的代码格式不正确吗?

c++ - 什么是 undefined reference /未解析的外部符号错误,我该如何解决?

ios - 我试图让 UILabel 在 UIScrollView 内部滚动,但它不滚动