【问题标题】:Create internal object based on argument in Constructor ?根据构造函数中的参数创建内部对象?
【发布时间】:2016-05-03 22:51:59
【问题描述】:

我有两个类 B 和 C(都派生自一个类 A)一个名为 H 的类,它持有 A 或 B。

代码:

class A  // abstract base class
{
  // bells and whistles
  // virtual fn 
     void fn() = 0 ; 
     protected:
         // some variables common to B and C
};

class B : public A  // inherit from A...
{
      B();
      fn(); // implement virtual function
      // bells and whistles
};

B::B() :A()
{
 // things
}

void B::fn()
{
 // things
}

// Class C : exactly the same as class B 


// Class H : holds B or C 
enum class CLASS_TYPE { TYPE_B, TYPE_C }

class H
{
   public:
      H(CLASS_TYPE type_);
      ~H();
   private: 
      A * _obj; 

};


H::H(CLASS_TYPE type_)
{
     switch(type_)
     {
     case CLASS_TYPE::B:
          _obj = new B();
          break;
     case CLASS_TYPE::C:
          _obj = new C();
          break;
     }
}

H::~H()
{
    delete _obj;// delete allocated object 
}

这是基于构造函数中的参数在类中创建内部对象的正确方法吗? 也是使用抽象基类,虚拟高效吗?这是大型模拟程序的一部分,我想避免性能损失。

谢谢。 PS:我尽量保持简单,如果需要更多信息,请告诉。

【问题讨论】:

    标签: c++ inheritance polymorphism virtual multiple-inheritance


    【解决方案1】:

    这是基于构造函数中的参数在类中创建内部对象的正确方法吗?

    我的第一个想法是摆脱enum。让类的用户构造一个对象,并用它构造一个H。

    将virtual成员函数clone()添加到A。

    将构造函数更改为接受A const&。使用clone() 成员函数在构造函数中复制输入对象。

    将H 中的成员变量更改为std::unique_ptr,而不是原始指针。

    这是我的建议:

    class A 
    {
       public:
          virtual A* clone() const = 0;
          virtual void fn() = 0 ; 
       protected:
    };
    
    class B : public A
    {
       public:
    
          virtual A* clone() const
          {
             return new B;
          }
    
          B();
          virtual void fn();
    };
    
    B::B() : A()
    {
    }
    
    void B::fn()
    {
    }
    
    #include <memory> // of std::unique_ptr
    class H
    {
       public:
    
          H(A const& a);
    
          // No need to have an explicit destructor.
          // The compiler generated destructor will do just fine.
          // ~H();
    
       private: 
          std::unique_ptr<A> aPtr_;
    };
    
    H::H(A const& a) : aPtr_(a.clone())
    {
    }
    

    【讨论】:

      【解决方案2】:

      你需要

      virtual void fn() = 0 ; 
      

      在 A 类和

      void fn() override;  // note: override is not strictly need but good practice
      

      B类和C类

      此外,您还必须处理复制和分配,因为您在类中有一个原始指针。直接逐个成员复制将导致两个 H 对象指向同一个 B/C。这将是非常糟糕的。因此,为了安全起见,您应该删除默认生成的副本/分配。更好的方法是尽可能避免使用原始指针。

      虚函数(多态)的性能成本很低。另见Cost of Polymorphic calls - C++

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2019-12-21
        • 2012-04-17
        • 1970-01-01
        • 2012-10-21
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多