我理解在钻石继承树中虚拟继承的效应,但不理解非钻石继承树中的副作用(如果有的话)。
如果你刚刚
class A;
class B: public virtual A;
这两个类的行为或内存布局(如果有的话)有什么不同,即构造函数调用的顺序等等。
假设class A
有数据成员。
请为您的回答提供正式文件
发布于 2017-02-07 12:27:28
虚拟继承的一个效果是,static_cast
下传不起作用。如果您想从虚拟基础向下转换,则必须使用dynamic_cast
。
A* pa = new B;
B* pb1 = static_cast<B*>(pa); // doesn't work: compilation error
B* pb2 = dynamic_cast<B*>(pa); // works
引用标准(5.2.9):
类型“cv1 B的指针”的prvalue,其中B是类类型,可以转换为“指向cv2 D的指针”.如果..。B既不是D的虚拟基类,也不是D的虚拟基类的基类。
发布于 2017-02-07 15:40:41
关于内存布局,一些编译器可能会将虚拟基的数据成员放在子类的数据成员之后(参见被认为有用的多重继承):
class A {
public:
int a;
};
class B : public virtual A {
public:
int b;
};
int main() {
B b;
std::cout << "&b.a < &b.b = " << (&(b.a) < &(b.b)) << std::endl; // &b.a < &b.b = = 0
return 0;
}
另一方面,非虚拟基的数据成员通常放在之前子数据成员:
class A {
public:
int a;
};
class B : public virtual A {
public:
int b;
};
int main() {
B b;
std::cout << "&b.a < &b.b = " << (&(b.a) < &(b.b)) << std::endl; // &b.a < &b.b = 1
return 0;
}
https://stackoverflow.com/questions/42098826
复制