仮想クラス

スポンサーリンク
スポンサーリンク
ライフスタイル関連のコンテンツ
お金 | 仕事 | 勉強 | プライベート | 健康 |
プログラミング関連のコンテンツ
C言語/C++入門 | Ruby入門 | Python入門 | プログラミング全般

基底クラスparentを継承する派生クラスchild_a, child_bがあり、さらにchild_a, child_b両方を継承するgrandクラスの定義を考えてみます。

スポンサーリンク

#include <iostream>
 
class parent {
public:
    int p;
};
 
class child_a : public parent {
public:
    int a;
};
 
class child_b : public parent {
public:
    int b;
};
 
class grand : public child_a, public child_b {
public:
    int g;
};
 
int main() {
    grand obj;
    obj.g = 10;
    obj.p = 10;  // エラーが起こる
 
    return 0;
};

普通に上記のようにクラス継承を書きますと・・・
「’p’ へのアクセスがあいまいです。」と、コンパイルエラーが起こってしまいます。

これは、pが基底クラスparentで宣言されており、child_aとchild_bのそれぞれで、parentを継承しているためです。
つまり、「grand obj;」と一番下のクラスのインスタンスからparent::pにアクセスする際に、継承が2回起こります。

この問題を避けるためには、仮想クラスを用います。
child_aとchild_bのparent継承の宣言に、virtualキーワードをつけます。

#include <iostream>
 
class parent {
public:
    int p;
};
 
class child_a : virtual public parent {
public:
    int a;
};
 
class child_b : virtual public parent {
public:
    int b;
};
 
class grand : public child_a, public child_b {
public:
    int g;
};
 
int main() {
    grand obj;
    obj.g = 10;
    obj.p = 10;
 
    return 0;
};

と書いてやると、エラーを起こさずに、「obj.p = 10;」と代入が行えます。
virtualキーワードで、parentクラスは1回の呼び出しとなります。

スポンサーリンク
 
スポンサーリンク