c ++中的简单单例示例

时间:2017-04-20 15:13:49

标签: c++

我正在尝试将以前在PHP和Java 8中使用过的单例实现为C ++。但我确实面临着语法和C ++如何工作(特别是指针)的某些限制。

这是我到目前为止所尝试的:

#include "iostream"

using namespace std;

class System{
protected:
    static System *obj;

public:
    static System *getInstance(){
        return obj;
    }

    void prn(){
        cout<<"this works!";
    }
};

int main(void){
    System &sys = System::getInstance();
    sys.prn();
}

执行时,我收到以下错误:

 sameer.cpp:20:10: error: non-const lvalue reference to type 'System'
 cannot bind
       to a temporary of type 'System *'
         System &sys = System::getInstance();
                 ^     ~~~~~~~~~~~~~~~~~~~~~

请帮我解决这个错误..因为我不知道这意味着什么。我在发布之前检查了论坛,它可能是以前问过的问题的可能重复(我无法找到)..但我发布了这个因为我想了解我的代码生成错误的含义。

感谢您的帮助

4 个答案:

答案 0 :(得分:4)

在C ++中,引用和指针是不同的东西。引用的行为与原始变量完全相同,而指针表示该变量的内存地址。您收到错误是因为您尝试将pointer-to-System分配给reference-to-System类型的变量,这不是同一件事。如果你真的想要,你可以使用System& sys = *ptr;语法取消引用指针,但在这种情况下,这是错误的做法;正确的解决方法是从getInstance()函数返回引用,而不是指针。

还有什么,在C ++中,您实际上可以在static函数中存储getInstance()实例变量。这是一个所谓的魔术静态&#34;,也称为&#34; Meyers Singleton&#34;,从C ++ 11开始,它保证你可以获得单例对象的线程安全构造。所以最终的解决方案是:

class System
{
private:
    System() {}

public:
    static System& getInstance(){
        static System theInstance;
        return theInstance;
    }

    void prn(){
        cout<<"this works!";
    }
};

int main()
{
    System& sys = System::getInstance();
    sys.prn();
}

另外,另外,你应该使用

#include <iostream>

#include "iostream"

包含标准库标头。你不需要在C ++中说main(void);空括号表示函数不带参数,因此main()会这样做。

答案 1 :(得分:2)

getInstance()返回一个指针,但您正在尝试调用它并将其绑定到引用。如果您希望它返回引用,请使其返回引用。

static System &getInstance(){
    return *obj;
}

答案 2 :(得分:0)

#include <iostream>
using namespace std;

class System{
private:
    static System *obj;
    System() {}

public:
    static System *getInstance()
    {
        if(obj == nullptr)
            obj = new System();
        return obj;
    }

    void prn(){
        cout<<"this works!"<< endl;
    }
};

System *System::obj;

int main(void){
    System *sys = System::getInstance();
    sys->prn();
}

答案 3 :(得分:-1)

懒惰初始化你的单身人士可能会很好。另外,请考虑将构造函数和单例设置为私有,以便您无法在其他任何位置创建实例。

#include "iostream"

using namespace std;

class System
{
private:
    static System *obj;
    System() {}

public:
    static System& getInstance(){
    if (nullptr == obj)
        obj = new System();

    return obj;
    }

    void prn(){
        cout<<"this works!";
    }
};

int main(void){
    System& sys = System::getInstance();
    sys.prn();
}