12

コンストラクターを宣言および定義する基本クラスがありますが、何らかの理由で、パブリックに派生したクラスがそのコンストラクターを認識していないため、派生クラスで転送コンストラクターを明示的に宣言する必要があります。

class WireCount0 {
protected:
    int m;
public:
    WireCount0(const int& rhs) { m = rhs; }
};

class WireCount1 : public WireCount0 {};

class WireCount2 : public WireCount0 {
public: 
  WireCount2(const int& rhs) : WireCount0(rhs) {}
};

int dummy(int argc, char* argv[]) {
    WireCount0 wireCount0(100);
    WireCount1 wireCount1(100);
    WireCount2 wireCount2(100);
    return 0;
}

上記のコードでは、WireCount1 wireCount1(100)宣言はコンパイラによって拒否されます (「'WireCount1::WireCount1(int)' の呼び出しに一致する関数はありません」) が、 mywireCount0wireCount2宣言は問題ありません。

に示されている明示的なコンストラクターを提供する必要がある理由を理解しているかどうかはわかりませんWireCount2。コンパイラが のデフォルトのコンストラクタを生成し、WireCount1そのコンストラクタがコンストラクタを隠しているWireCount0ためですか?

参考までに、コンパイラはi686-apple-darwin10-gcc-4.2.1 (GCC) 4.2.1 (Apple Inc. build 5659).

4

3 に答える 3

15

コンストラクターは継承されません。派生クラスのコンストラクターを作成する必要があります。さらに、派生クラスのコンストラクターは、基本クラスのコンストラクターを呼び出す必要があります。

于 2010-07-10T01:37:56.607 に答える
9

すべての派生クラスは、基本クラスのコンストラクターを何らかの形で呼び出す必要があります。

オーバーロードされたコンストラクターを作成すると、既定のコンパイラによって生成されたパラメーターなしのコンストラクターが表示されなくなり、派生クラスはオーバーロードされたコンストラクターを呼び出す必要があります。

あなたがこのようなものを持っているとき:

class Class0 {
}

class Class1 : public Class0 {
}

コンパイラは実際にこれを生成します:

class Class0 {
public:
  Class0(){}
}

class Class1 : public Class0 {
  Class1() : Class0(){}
}

デフォルト以外のコンストラクターがある場合、パラメーターなしのコンストラクターは生成されなくなりました。以下を定義する場合:

class Class0 {
public:
  Class0(int param){}
}

class Class1 : public Class0 {
}

コンパイラは、基本クラスのコンストラクターを呼び出すために Class1 にコンストラクターを生成しなくなりました。明示的に自分で行う必要があります。

于 2010-07-10T01:41:15.083 に答える
1

派生を扱う前に、基本クラスを構築する必要があります。自明ではないコンストラクターを使用して派生クラスを構築すると、コンパイラーはベースに対して何を呼び出すかを決定できないため、エラーが発生します。

于 2010-07-10T01:43:18.153 に答える