像默认构造函数或析构函数

像默认构造函数或析构函数

本文介绍了为什么不复制构造函数“链接”像默认构造函数或析构函数?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这可能是一个有明显答案或重复的问题。



为什么没有链接复制构造函数(如默认的ctors或dtors),所以在派生类的复制构造函数被调用之前,基类的复制构造函数被调用?使用复制构造函数和析构函数,它们分别在从基础到派生和派生到基础的链中被调用。为什么不是这种情况下复制构造函数?例如,此代码:

  class Base {
public:
Base():basedata ()){}

Base(const Base& src):basedata(src.basedata){
cout< Base :: Base(const Base&)<< endl;
}

void printdata(){
cout<基于数据<< endl;
}

private:
int basedata;
};

class Derived:public Base {
public:
Derived(){}

Derived(const Derived& d){
cout << Derived :: Derived(const Derived&)<< endl;
}
};


srand(time(0));


派生d1; // basedata初始化为rand()感谢Base :: Base()

d1.printdata(); //打印随机数

派生d2 = d1; //基础数据从Base :: Base()再次初始化为rand()
// Derived :: Derived(const Derived&)被调用,但不是
// Base :: Base(const Base& )

d2.printdata(); //打印不同的随机数

复制构造函数不会因为 Derived :: Derived(const Derived&)无法访问 basedata 来更改对象的副本。 / p>

有一些基本的东西我缺少关于复制构造函数,所以我的心理模型是不正确的,或有一些奥术的(或不神秘的)这个设计的原因吗?复制构造函数不会(不能)真正地创建对象的副本,因为 code> Derived :: Derived(const Derived&)无法访问 pdata 以更改它。


当然可以:

  Derived(const Derived& d )
:Base(d)
{
cout<< Derived :: Derived(const B&)<< endl;
}

如果不在初始化器列表中指定基类构造函数,默认构造函数被调用。如果你想调用默认构造函数以外的构造函数,你必须指定你想要调用的构造函数(以及使用哪个参数)。



为什么会出现这种情况:为什么复制构造函数与任何其他构造函数不同?作为一个实际问题的例子:

  struct Base 
{
Base(){}
Base(Base volatile&){} //(1)
Base(Base const&){} //(2)
};

struct Derived:Base
{
Derived(Derived&){}
};

Base 期望 Derived 复制构造函数调用?


This might be a question with an obvious answer or a duplicate. If so, sorry, I'll delete it.

Why aren't copy constructors chained (like default ctors or dtors) so that before the derived class's copy constructor is called, the base class's copy constructor is called? With copy constructors and destructors, they are called in a chain from base-to-derived and derived-to-base, respectively. Why isn't this the case for copy constructors? For example, this code:

class Base {
public:
    Base() : basedata(rand()) { }

    Base(const Base& src) : basedata(src.basedata) {
        cout << "Base::Base(const Base&)" << endl;
    }

    void printdata() {
        cout << basedata << endl;
    }

private:
    int basedata;
};

class Derived : public Base {
public:
    Derived() { }

    Derived(const Derived& d) {
        cout << "Derived::Derived(const Derived&)" << endl;
    }
};


srand(time(0));


Derived d1;      // basedata is initialised to rand() thanks to Base::Base()

d1.printdata();  // prints the random number

Derived d2 = d1; // basedata is initialised to rand() again from Base::Base()
                 // Derived::Derived(const Derived&) is called but not
                 // Base::Base(const Base&)

d2.printdata();  // prints a different random number

The copy constructor doesn't (can't) really make a copy of the object because Derived::Derived(const Derived&) can't access basedata to change it.

Is there something fundamental I'm missing about copy constructors so that my mental model is incorrect, or is there some arcane (or not arcane) reason for this design?

解决方案

Sure it can:

Derived(const Derived& d)
    : Base(d)
{
    cout << "Derived::Derived(const B&)" << endl;
}

If you don't specify a base class constructor in the initializer list, its default constructor is called. If you want a constructor other than the default constructor to be called, you must specify which constructor (and with which arguments) you want to call.

As for why this is the case: why should a copy constructor be any different from any other constructor? As an example of a practical problem:

struct Base
{
    Base() { }
    Base(Base volatile&) { } // (1)
    Base(Base const&)    { } // (2)
};

struct Derived : Base
{
    Derived(Derived&) { }
};

Which of the Base copy constructors would you expect the Derived copy constructor call?

这篇关于为什么不复制构造函数“链接”像默认构造函数或析构函数?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-18 13:27