5

私は現在、SDL を使用して趣味で 2D ゲーム エンジンをプログラミングしながら、C++11 スマート ポインターの使用方法を学んでいます。しかし、SDL の OOp ラッパーを実装しているときに問題が発生しました。

その意図は、構築時に SDL を初期化し、破棄されたときに SDL をシャットダウンするシングルトン クラスを作成することです。getInstanceシングルトン クラスには、シングルトンにa を返す静的メソッドがshared_ptrあり、インスタンスが存在しない場合は単一のインスタンスを構築します。これは、シングルトンのすべてのクライアントがそれに対する ashared_ptrを所有し、すべてのクライアントが破棄されると、シングルトンも破棄されるという考え方です。 . シングルトン (およびその他のグローバル) が一般的に悪いことは理解していますが、SDL ライブラリは 1 つしか使用できないため、これはシングルトンが適切な数少ないケースの 1 つになる可能性があると思います。

問題は、メソッドshared_ptrからを返すことにあります。同じマネージャー オブジェクトgetInstanceを使用する代わりに、インスタンスは無関係であり、そのうちの 1 つを破棄するとシングルトンの割り当てが解除されます。shared_ptrshared_ptr

#include <iostream>
#include <memory>
using namespace std;

class Foo
{
public:
    ~Foo(){cout << "Foo <" << this << "> destroyed\n"; instance_ = nullptr;}
    static shared_ptr<Foo> getInstance()
    {
        if(instance_ == nullptr)
            instance_ = new Foo;
        //problem: the shared pointers created are unaware of each other
        return shared_ptr<Foo>(instance_);
    }
private:
    Foo(){cout << "Foo <" << this << "> constructed\n";}
    Foo(Foo& other){}
    void operator=(Foo& other){}
    static Foo* instance_;
};

Foo* Foo::instance_ = nullptr;

int main()
{
    shared_ptr<Foo> a = Foo::getInstance();
    shared_ptr<Foo> b = Foo::getInstance();
    shared_ptr<Foo> c = Foo::getInstance();
}

出力:

Foo <0x3e2a10> constructed
Foo <0x3e2a10> destroyed
Foo <0x3e2a10> destroyed
Foo <0x3e2a10> destroyed
4

2 に答える 2