84

daughter次のコードで、タイプのオブジェクトをインスタンス化すると、デフォルトのgrandmother()コンストラクターが呼び出される理由がわかりません。

grandmother(int)コンストラクターを呼び出すか(クラスコンストラクターの仕様に従うmotherため)、仮想継承のためにこのコードをまったくコンパイルしないようにする必要があると思いました。

ここで、コンパイラーgrandmotherは私の背中でデフォルトのコンストラクターを黙って呼び出しますが、私はそれを要求しませんでした。

#include <iostream>

class grandmother {
public:
    grandmother() {
        std::cout << "grandmother (default)" << std::endl;
    }
    grandmother(int attr) {
        std::cout << "grandmother: " << attr << std::endl;
    }
};

class mother: virtual public grandmother {
public:
    mother(int attr) : grandmother(attr) {
        std::cout << "mother: " << attr << std::endl;
    }
};

class daughter: virtual public mother {
public:
    daughter(int attr) : mother(attr) {
        std::cout << "daughter: " << attr << std::endl;
    }
};

int main() {
  daughter x(0);
}
4

1 に答える 1

92

仮想継承を使用する場合、仮想基本クラスのコンストラクターは、最も派生したクラスのコンストラクターによって直接呼び出されます。この場合、daughterコンストラクターはコンストラクターを直接呼び出しますgrandmother

初期化リストでコンストラクターを明示的に呼び出さなかったためgrandmother、デフォルトのコンストラクターが呼び出されます。正しいコンストラクターを呼び出すには、次のように変更します。

daugther(int attr) : grandmother(attr), mother(attr) { ... }

このFAQエントリも参照してください。

于 2012-03-28T12:58:12.100 に答える