C++ 通过C+中的静态实例实现单例+;——到源文件还是到头文件?

C++ 通过C+中的静态实例实现单例+;——到源文件还是到头文件?,c++,singleton,compiler-construction,C++,Singleton,Compiler Construction,干杯 我在“通过示例编程游戏AI”中遇到了这段代码: 我被作者的事实陈述弄糊涂了,即header中的函数中静态声明的变量将导致声明多个独立的静态变量实例。我不认为我在通常的getInstance()函数实现中见过这种行为,我经常将其放入头中(除了我喜欢玩指针和在第一次使用时初始化单例)。我在工作中使用GCC 那么标准怎么说呢?不兼容的编译器会怎么说?作者的陈述是否正确,如果是,你能说出一些编译器是否会创建多个实例,如果在代码头中声明了代码> GestStand()/Cux>?< /P> < P>

干杯

我在“通过示例编程游戏AI”中遇到了这段代码:

我被作者的事实陈述弄糊涂了,即header中的函数中静态声明的变量将导致声明多个独立的静态变量
实例
。我不认为我在通常的
getInstance()
函数实现中见过这种行为,我经常将其放入头中(除了我喜欢玩指针和在第一次使用时初始化单例)。我在工作中使用GCC


那么标准怎么说呢?不兼容的编译器会怎么说?作者的陈述是否正确,如果是,你能说出一些编译器是否会创建多个实例,如果在代码头中声明了代码> GestStand()/Cux>?< /P> < P> C++中没有任何东西阻止内联函数有一个静态变量,编译器必须安排使所有翻译单位之间的变量是通用的。(就像模板实例化静态类成员和静态函数变量一样)

外部内联
函数中的
静态
变量始终引用同一对象


请注意,在C中,内联函数不能有静态变量(也不能引用具有内部链接的对象)。

我用四种方式尝试了OP在VS2008中发布的代码,并且
MyClass
的静态实例在
MyClass::instance()中似乎没有问题

  • Instance()
    在中定义 MyClass.cpp:这是正常的方式 一切都很好
  • Instance()
    仅在 类声明。这是 一切都很好
  • Instance()
    定义为
    inline
    在类之外,但在标题中 一切都很好
  • 如3所示,但不带内联
    和
    链接者说有多种定义
    
    Instance()

  • 我认为本书的作者关注的是上面的4,并且知道MyClass的静态实例将在编译和链接的程序中得到处理。

    换句话说,在MyClass.h中的“静态内联函数”中定义的“静态变量”将在生成的链接代码中只出现一次,并且将在源文件之间共享(例如main.cpp、myclass.cpp和joetheplumber.cpp)?Moving::Instance()从上面的代码到头文件,仍然可以保证将相同的实例返回到不同的.cpp文件?只要编译器符合要求。因为我不记得有任何问题,而且模板需要具备可移植性,所以我不担心这一点。我没有听说过最近在这方面的问题,也没有听说过VC6或GCC 2.95。有人提到共享objECTS/DLL,我刚刚检查了Linux和Solaris,他们没有问题。我把你们标记为接受,但是我已经和AProgrammer一起做了,而且我觉得切换TICK很糟糕。所以这里只是一个非常清晰的推理的投票。关于如何实现一个单独的,以及C++中的线程安全的讨论,可以在THI中找到。s文件:
    /* ------------------ MyClass.h -------------------- */
    #ifndef MY_SINGLETON
    #define MY_SINGLETON
    
    class MyClass
    {
    private:
    
      // member data
      int m_iNum;
    
      //constructor is private
      MyClass(){}
    
      //copy ctor and assignment should be private
      MyClass(const MyClass &);
      MyClass& operator=(const MyClass &);
    
    public:
    
      //strictly speaking, the destructor of a singleton should be private but some
      //compilers have problems with this so I've left them as public in all the
      //examples in this book
      ~MyClass();
    
      //methods
      int GetVal()const{return m_iNum;}
      static MyClass* Instance();
    };
    
    #endif
    
    /* -------------------- MyClass.cpp ------------------- */
    
    //this must reside in the cpp file; otherwise, an instance will be created
    //for every file in which the header is included
    MyClass* MyClass::Instance()
    {
      static MyClass instance;
    
      return &instance;
    }