我曾尝试做一些练习,当我终于认为自己理解时,就会出现一种破坏一切的练习。 例如,我有以下类:
class A
{
public:
A() {std::cout<<"A()";}
virtual ~A(){std::cout<<"~A()";}
virtual void print() {std::cout<<"A";}
};
class B : public A
{
public:
B() {std::cout<<"B()";}
virtual ~B(){std::cout<<"~B()";}
virtual void print() {std::cout<<"B";}
};
以下代码片段:
void f3()
{
A a[2];
a[1]=B();
a[1].print();
}
结果我认为:
A() A()
A() B() {not sure why there is an A() too)
A - and here I really don't know because either A and B are virtual(and I have in the notebook A)
~B() ~A()
~A() ~A()
另一个代码片段:
void f4()
{
A* a[]={new A(), new B()};
a[0]->print();
a[1]->print();
delete a[0];
delete a[1];
}
这也是一个问题。我们有
A() {here I don t know why there is an A()}
A() B()
A
B
~B() ~A()
A()
但这是对的吗?为什么在这里我们有A和B而不是B和A?我的意思是,在第一个练习中,我有A,当它是B()的类型时,在这里它是我认为它是正常的,但为什么?
答案 0 :(得分:2)
A() A()
您创建了一个包含两个A的数组,因此两次调用A ctor。
A() B() {not sure why there is an A() too)
你创建了一个B(B()
),而Bs是从As派生的,所以步骤是:分配内存来存储B,调用A的ctor为A部分,调用B的ctor为B部分。
A - and here I really don't know because either A and B are virtual(and I have in the notebook A)
您已将新创建的B分配给A,因此这会导致B的A部分副本到达目的地A.然后您在A上调用print
,这会打印{{1} }。
A
dtors被称为与ctors完全相反。
在第二次尝试中,您使用指针和动态分配,在这种情况下使用多态。你的数组是一个两个指向A类型的指针的数组,用两个对象的(地址)初始化:第一个开始A,第二个开始是B。
当您致电~B() ~A()
~A() ~A()
时,a[0]->print()
是A的地址,因此会调用其a[0]
方法。
当您致电print
时,a[1]->print()
是B的地址,因此会调用其a[1]
方法,因为print
为print
。