在菱形继承问题之外使用虚拟继承来允许越级

问题描述

考虑以下程序:

#include <iostream>
#include <string>

class B
{
public:
    int n;

    B() : n(0) {}
    B(int m) : n(m) {}
};

class D1 : virtual public B
{
public:
    int a;
    
    D1() : a(0) {}
    D1(int m) : a(m) {}
};

class D2 : public D1
{
public:
    int d;
    
    D2() : d(0) {}
    D2(int m) : d(m) {}
    D2(int j,int k) : d(j),D1(k) {}
    D2(int i,int j,int k) : d(i),D1(j),B(k) {}  //Without virtual inheritance,//must add new constructor to D1.
};

int main()
{
    std::string s;
    D2 d2(0,1,2);
    
    std::cout << "d2.n = " << d2.n << "\n";
    std::cout << "d2.a = " << d2.a << "\n";
    std::cout << "d2.d = " << d2.d << "\n";
    
    std::cout << "Press ENTER to exit.\n";
    getline(std::cin,s);
}

让 D1 从 B 虚拟继承允许我从 D2 的构造函数调用 B 的构造函数,跳过类 D1。

除了钻石继承问题之外,这种虚拟继承的使用是否会导致未定义的行为或其他危害?

除了解决菱形继承问题之外,我从未见过使用虚拟继承。

解决方法

除了钻石继承问题之外,这种虚拟继承的使用是否会导致未定义的行为或其他危害?

无论出于何种目的,虚拟继承都会招致这些“危害”:

  • 通过指针访问虚拟基类,这可能会比较慢
  • 每个派生类,无论深度如何,都必须负责构建虚拟基
  • 从虚拟基础向下转型必须通过 dynamic_cast 完成。更快的 static_cast 是不可能的。

您的示例不会引入任何其他虚拟继承用法不存在的未定义行为或危害。