分类: C/C++
2007-09-16 21:40:16
virtual 继承的作用: 避免内存中父虚基类成员的重复放置。一般用于多继承情况下。
#include
class A{
public:
virtual void f(){
printf("Hi,I'm in A::f();\n");
};
};
class B: virtual public A{
public:
void f(){
printf("Hi,I'm in B::f();\n");
};
};
class C: virtual public A{
public:
void f(){
printf("Hi,I'm in C::f();\n");
};
};
class D: public C, public B{};
int main()
{
D d;
//d.f();
d.C::f();
return 0;
}
B和C中不能都重载函数f,否则编译器将会报错。若B和C都不虚继承基类A,那么在main中只能用d.C::f()这种方式显式调用父类中的函数,但是如果是虚继承,则可直接用d.f()这种格式。
画形表示如下:
没virtual virtual继承时:
A A A
\ / / \
B C B C
\ / \ /
D D
虚继承基本上是与多重继承联系在一起的,所以JAVA好像就没什么虚继承,因为JAVA不支持多重继承。还有些人认为多重继承的引入降低了一些效率,不过不是很大,可以忽略掉吧。
iostream中基类好像是ios,然后istream从ios虚继承,ostream从ios虚继承,而iostream就是从上面两个继承的。这里面也是一样的原理。
多重继承中,每个最后派生的类都必须初始化基类,因为编译器无法知道使用那个派生类来初始化基类的,因此总在最后派生类中具体指出。
如果创造一个基类的缺省构造函数,那么可将基类视为黑箱。在多重继承时,用一个对象可有不同的this指针,这可由将派生类转换为各个基类看出,派生类起始地址与基类列表第一个类的地址一致,第二个基类地址随后,然后是根据声明次序安排成员对象地址。