构造函数调用虚函数时的混淆

时间:2015-07-09 06:14:55

标签: c++ inheritance constructor object-slicing

构造函数中的混淆通过临时对象作为函数中的参数进行调用

#include <iostream>
using namespace std;

class Base
{
   protected:

      int i;

   public:

      Base() {
         cout<<"\n Default constructor of Base \n";
      }

      Base(int a)
      {
         i = a;        
         cout<<"Base constructor \n"; 
      }

      void display(){ 
         cout << "\nI am Base class object, i = " << i ;
      }

      ~Base(){
         cout<<"\nDestructor of Base\n";
      }
};

class Derived : public Base
{
   int j;

   public:

   Derived(int a, int b) : Base(a) { 
      j = b; 
      cout<<"Derived constructor\n"; 
   }

   void display()   { 
      cout << "\nI am Derived class object, i = "<< i << ", j = " << j; 
   }

   ~Derived(){
      cout<<"\nDestructor Of Derived \n";
   }
};


void somefunc (Base obj)    //Why there is no call to default constructor of Base class 
{
   obj.display();
}


int main()
{

   Base b(33);

   Derived d(45, 54);

   somefunc( b) ;

   somefunc(d); // Object Slicing, the member j of d is sliced off

   return 0;
}

我的问题是,当我们在函数中创建Base类的临时对象时,为什么没有调用Base Class的Default Constructor(void somefunc(Base obj))

3 个答案:

答案 0 :(得分:4)

  

我的问题是,当我们在函数中创建Base类的临时对象时,为什么没有调用Base Class的Default Constructor

Base的实例是在调用somefunc时使用复制构造函数构造的。该对象不是使用默认构造函数构造的。由于您尚未定义默认复制构造函数,因此编译器会创建默认复制构造函数。

答案 1 :(得分:3)

它不是临时对象。参数通过值传递给函数,因此将调用copy ctor,而不是默认ctor。请注意,如果没有用户定义,编译器将提供复制构造函数,您可以自己定义它以输出一些调试信息。

Base(const Base& a) : i (a.i) 
{
    cout<<"Base copy constructor \n"; 
}

答案 2 :(得分:1)

它将调用copy construct函数来在函数

中创建Base类的Temporary对象