C++的构造函数调用虚函数
请问一下各位C++高手:
#include <iostream>
using namespace std;
class A
{
public :
A()
{
p() ;
}
virtual void p() {cout<<"A:"<<sizeof(A)<<endl;};
};
class B : public A
{
public:
int i;
B():i(10)
{
p();
}
virtual void p(){cout<<"B:"<<sizeof(B)<<endl;} ;
};
int main()
{
B b;
system("pause");
}
在A的构造函数里面调用的为什么是A::p()呢?是不是B::p()还没有构造,所以只能构造A::p()?按照虚函数的性质,应该是调用B::p()的啊
参考答案:的确如你所想,继承类在构造的时候总是(记住这个“总是”)首要调用基类的构造函数来对属于基类的部分进行构造,在这个时候整个类都是被当作基类来处理的,继承类的部分此对C++来说好象不存在一样,直到继承类的构造函数被调用并构造以后,该类才被当作继承类类处理;对于析构也是一样。你可以从下面代码的执行情况中看出:
#include <iostream>
#include <typeinfo>
using namespace std;
class A
{
public:
A()
{
cout << "Type name of *this: " << typeid(*this).name() << endl;
}
};
class B : public A
{
public:
B()
{
cout << "Type name of *this: " << typeid(*this).name() << endl;
}
};
int main()
{
B b;
}
按照虚函数的性质,按道理是调用B::p(),但如果此时调用的是子类的函数的p(),由于子类并没有构造,所以调用p()函数所使用的数据成员包含的其实是垃圾,这将导致不可预料的未定义行为和后期的大量调试,对于这种本质上就危险的行为C++是没有理由让你去做它的。
参见Effective C++
条款9:Never call virtual functions during construction or destruction
Scott Meyers已经解释得很详细了...