1

我正在遵循这种单例模式,为什么在这种情况下会出现错误 LNK2001: unresolved external symbol?我的问题看起来很相似,但我的问题不在于静态实例的定义。我的问题是解决另一个类的静态GetInstance()定义。

我的错误似乎不同,或者以前的答案不充分。我已经尝试过建议,“你需要在课堂之外定义 s_instance”,这对我作为一个 cpp 菜鸟来说没有意义。我在标头中声明静态,并在 cpp 中定义它们的实现。

我也不需要关于单例线程安全的讲座,处理程序绑定使用信号2...

状态.h

class State
{   
public: 
    State(void);
    ~State(void);

    static State* instance; 
    static State* GetInstance(); 
... 

};

状态.cpp

State::AppState mCurrentState;
boost::signals2::signal<void ()> mSignal;


State* instance = NULL;
State* GetInstance()
{
    if( instance == NULL)
    {
        instance = new State();
        return instance;
    }
    else
    {
        return instance;
    }
}

所有这些都编译得很好。然后,当我尝试像这样访问单例时 State *state = State::GetInstance();,出现“未解析的外部符号”错误。

错误 LNK2019:未解析的外部符号“public:static class State * __cdecl State::GetInstance(void)”(?GetInstance@State@@SAPAV1@XZ) 在函数“public: virtual void __thiscall MesherApp::setup(void)”中引用(?setup@MesherApp@@UAEXXZ)

还尝试了以下内容,因为有人说“在课堂外定义”——这甚至意味着什么?

class State
{
   public:
   ...
}
static State* instance; 
static State* GetInstance(); 

看看这个问题,我不知道这是如何应用的带有字段的静态方法。我在 .h 中声明并在 cpp 文件中定义所有内容。

4

2 回答 2

5

你能简化吗?

class State
{
   public:

      static State& GetInstance() 
      {
          static State _instance; 
          return _instance;
      }
};

看,它是隐藏的,它是按需的,它是线程安全的,并且它可以在没有跳跃的情况下工作。

静态初始化确保等效于instance == NULL那里,而无需任何额外的努力。它还确保在(之前)进程关闭(假设正常终止)时正确销毁。

这样做的唯一假设是您不希望能够“强制”重置单例实例。

于 2013-09-12T22:34:57.950 回答
2

我认为这个答案是合适的,如果我发现自己使用单例,我会扎根。

另一方面,您的代码存在问题:

State* instance = NULL;

它应该是

State* State::instance = NULL;

我还刚刚注意到另一个错误是:

State* GetInstance()
{
    //...
}

应该:

State* State::GetInstance()
{
    //...
}
于 2013-09-12T23:09:36.437 回答