5

重複の可能性:
コンストラクター内での仮想関数の呼び出し

クラス Shape とそのサブクラス Sphere があります。

//Shape : 

class Shape
{
    public:
        Shape(const string& name);
        virtual ~Shape();

        virtual string getName();

    protected:

        string mName;

};

Shape::Shape(const string& name) : mName(name)
{
   /*Some stuff proper to Shape*/

   /*Some stuff proper to subclass (sphere)*/

   /*Some stuff proper to Shape*/
}

Shape::~Shape(){}

string Shape::getName(){ return mName; }


//Sphere :

class Sphere : public Shape
{
    public:
        Sphere(const string& name, const float radius);
        virtual ~Sphere();

        virtual string getRadius();

    protected:

        float mRadius;
}

Sphere::Sphere(const string& name, const float radius) : Shape(name), mRadius(radius)
{
   /*Some stuff*/
}

Sphere::~Sphere(){}

float Sphere::getRadius(){ return mRadius; }

では、 Shape コンストラクターでサブクラスのものをどのように処理できますか? テンプレート メソッド パターンに頼ることもでき ますが、コンストラクターで純粋仮想関数を呼び出さなければなりません。私は試しましたが、コンパイラはそれを好きではありませんでした

編集

コンストラクターを新しいメソッド「init」に移動することにしました。仮想メソッドは「subInit」になります。

//Shape : 

class Shape
{
    public:
        Shape(const string& name);
        virtual ~Shape();

        virtual string getName();

        virtual void init();

    protected:

        string mName;

        virtual void subInit() = 0;

};

Shape::Shape(const string& name) : mName(name){}

Shape::~Shape(){}

string Shape::getName(){ return mName; }

void Shape::init()
{
   /*Some stuff proper to Shape*/

   /*Some stuff proper to subclass (sphere)*/
   /*Call to the pure virtual function subInit*/

   subInit();

   /*Some stuff proper to Shape*/
}

//Sphere : 

class Sphere : public Shape
{
    public:
         Sphere(const string& name, const float radius);
         virtual ~Sphere();

         virtual string getRadius();

        protected:

            float mRadius;

            void subInit();
    }

    Sphere::Sphere(const string& name, const float radius) : Shape(name),mRadius(radius)
    {}

    Sphere::~Sphere(){}

    float Sphere::getRadius(){ return mRadius; }

    Sphere::subInit()
    {
       /*Some stuff previously in the constructor*/
    }

基本的にはテンプレートメソッドのパターンです

クライアントは次のように書き込みます。

Shape* sphere = new Sphere();
sphere->init();

それから私は私の答えを持っています:少なくともC ++では、コンストラクターでこのパターンを適用することは不可能です

4

1 に答える 1

1
Shape::Shape(const string& name) : mName(name)
{
   /*Some stuff proper to Shape*/

   /*Some stuff proper to subclass (sphere)*/

   /*Some stuff proper to Shape*/
}

サブクラスに固有のものは、サブクラスが存在するまで実行できないため、サブクラスのコンストラクターに入れる必要があります。後のものは、サブクラスのコンストラクターによって呼び出される関数に入れることができます。

Shape::Shape(const string& name) : mName(name)
{
   /*Some stuff proper to Shape*/
}

void Shape::finishConstruction()
{   
   /*Some stuff proper to Shape*/
}

Sphere::Sphere(const string& name, const float radius)
: Shape(name), mRadius(radius)
{
    /*Some stuff proper to subclass (sphere)*/

    finishConstruction();
}
于 2013-01-27T21:49:56.007 に答える