web-dev-qa-db-ja.com

C ++でプライベートコンストラクターが必要な場合

C++のプライベートコンストラクタについて質問がありますが、コンストラクタがプライベートの場合、クラスのインスタンスを作成するにはどうすればよいですか?クラス内にgetInstance()メソッドが必要ですか?

38
user707549

privateコンストラクターを使用するシナリオはいくつかあります。

  1. friendsを除くすべてのオブジェクトの作成を制限します。この場合、すべてのコンストラクターはprivateでなければなりません

    _class A
    {
    private:
       A () {}
    public:
       // other accessible methods
       friend class B;
    };
    
    class B
    {
    public:
       A* Create_A () { return new A; }  // creation rights only with `B`
    };
    _
  2. 特定のタイプのコンストラクター(つまり、コピーコンストラクター、デフォルトコンストラクター)を制限します。例えば_std::fstream_は、このようなアクセスできないコンストラクターによるコピーを許可しません

  3. 外側の世界に公開されることを想定していない、共通のデリゲートコンストラクターを作成するには:

    _class A
    {
    private: 
      int x_;
      A (const int x) : x_(x) {} // common delegate; but within limits of `A`
    public:
      A (const B& b) : A(b.x_) {}
      A (const C& c) : A(c.foo()) {}
    };
    _
  4. シングルトンパターン シングルトンclassが継承可能でない場合(継承可能な場合はprotectedコンストラクターを使用)

    _class A
    {
    public:
       A();
       A(int);
    private:
       A(const A&);  // Neither others nor `friend` can use this
       // A(const A&) = delete;  // C++11 equivalent `private` doesn't matter
    };
    _

Clarification:シングルトンの場合、一般的な方法は、privateコンストラクターにアクセスできるpublic: static getInstance()メソッドをクラス内に持つことです。最終的には、オブジェクトを作成して外部の世界に提供します。

_    class Singleton
    {
    public:
       static Singleton& getInstance() {
          Singleton object; // invokes the `private` constructor
          return object;
       }
    private:
       Singleton() {}  // make `protected` for further inheritance
       Singleton(const Singleton&);  // inaccessible
       Singleton& operator=(const Singleton&);  // inaccessible
    };
_
43
iammilind

プライベートコンストラクターは、一般的にBuilderメソッドで使用されます。たとえば、Named Constructorイディオムなどです。

class Point
{
public:
  static Point Polar(double, double);
  static Point Cartesian(double, double);
private:
  Point(double,double);
};

この(典型的な)例では、Named Constructorイディオムを使用して、Pointオブジェクトの構築に使用する座標系を明示的にしています。

12
Matthieu M.

プライベートコンストラクターは、クラスのオブジェクト作成を制御する場合に役立ちます。コードで試してみましょう

#include <iostream>
using namespace std;
class aTestClass
{
    aTestClass()//////////private constructor of this class
    {
        cout<<"Object created\n";
    }
    public:

};
int main()
{
    aTestClass a;
    aTestClass *anObject;
}

aTestClass aという行は、この行がプライベートなconstructor.commentに間接的にアクセスしてプログラムを実行しようとしているため、エラーを引き起こします。 。別のプログラムを書きましょう。

#include <iostream>
using namespace std;
class aTestClass
{
    aTestClass()//////////private constructor of this class
    {
        cout<<"Object created\n";
    }
    public:

    aTestClass* getAnObject()/////a public method create an object of this class and return the address of an object of that class
    {

        return (new aTestClass);

    }
};
int main()
{
    //aTestClass a;
    aTestClass *anObject=NULL;
    anObject=anObject->getAnObject();
}

出力は

Object created

そのため、プライベートコンストラクターを含むクラスのオブジェクトを作成しました。 Use this concept to implement singleton classありがとう

10

はい、これは一般的に シングルトンパターン で使用され、静的メンバー関数を介してオブジェクトにアクセスします。

4
murrekatt

一部のコンストラクターがプライベートの場合、クラス自体(および友人)以外は誰もそのコンストラクターを使用してそのインスタンスを作成できないことを意味します。したがって、getInstance()などの静的メソッドを提供して、クラスのインスタンスを作成したり、フレンドクラス/メソッドでインスタンスを作成したりできます。

2
devil

そもそもコンストラクターがプライベートにされた理由に依存します(編集しているクラスを書いた人に尋ねるべきです)。時には、コンストラクターをプライベートにして、コピーの構築を禁止することがあります(ただし、他のコンストラクターによる構築は許可されます)。また、クラスの「フレンド」以外のクラスの作成を禁止するために、コンストラクターをプライベートにすることもできます(これは、クラスが、ヘルパークラスが使用するクラスのみが使用する「ヘルパー」である場合によく行われます作成されました)。 (通常は静的な)作成関数の使用を強制するために、コンストラクターをプライベートにすることもできます。

C++のプライベートコンストラクターを使用して、定数構造のオブジェクト作成を制限できます。そして、enumのような同じスコープで同様の定数を定義できます

struct MathConst{
    static const uint8 ANG_180 = 180;
    static const uint8 ANG_90  = 90;

    private:
        MathConst(); // restricting object creation
};

MathConst::ANG_180のようなアクセス

0
C_Raj