3

派生クラスのmovectorを介して、基本クラスのmove ctorを明示的に呼び出そうとしていますが、驚いています。、これは実際には、基本クラスのmovectorではなく基本クラスのcopyctorを呼び出します。

オブジェクトで関数を使用std::move()して、派生したmovectorが呼び出されていることを確認しています。

コード:

class Base
{
public:
    Base(const Base& rhs){ cout << "base copy ctor" << endl; }
    Base(Base&& rhs){ cout << "base move ctor" << endl; }
};

class Derived : public Base
{
public:

    Derived(Derived&& rhs) : Base(rhs) { cout << "derived move ctor"; }
    Derived(const Derived& rhs) : Base(rhs) { cout << "derived copy ctor" << endl; }
};

int main()
{
    Derived a;
    Derived y = std::move(a); // invoke move ctor
    cin.ignore();
    return 0;
}

プログラム出力:

ベースコピーコンストラクタ

派生移動コンストラクタ

ご覧のとおり、基本クラスのmove ctorは忘れられているので、どのように呼ぶのですか?

4

3 に答える 3

5

Derivedクラスのコンテキストでは、パラメータrhsには明らかに名前があります。したがって、左辺値である必要があり、右辺値にすることはできません。ただし、T&&右辺値にバインドするのは1つだけです。基本クラスのmoveコンストラクターを呼び出す場合は、次のようなコードを使用する必要があります。

Derived(Derived&& rhs): Base(std::move(rhs)) { std::cout << "derived move ctor"; }

これにより、のmoveコンストラクターが呼び出され、BaseBase一部が移動されrhsます。メンバーBaseについては何も知らないため、 moveコンストラクターはによって追加されたものを移動しません。DerivedBaseDerived

于 2012-01-17T00:42:06.017 に答える
2

コンストラクター、または署名に含まれるその他の関数やメソッドは、&&次の両方の条件が満たされる場合にのみ、コンパイラーによって選択される資格があります。

  • 渡す式のデータ型はまたはT&&ですT。-つまりT&、受け入れられません
  • そしてそれは実際には右辺値でなければなりません-例えば関数から(値TまたはによってT&&)返されます。

move(rhs)これらの両方の条件を満たす。は正しいタイプですが、。を必要とする関数に渡される資格があると見なされる前にrhs、実際には関数(など)から返される必要があります。move&&

于 2012-01-17T00:59:04.153 に答える
1

基本クラスのmoveコンストラクターが使用された場合、派生コンストラクターはmoved-fromオブジェクトにアクセスできます。これは危険なので、オブジェクトの使用が終了し、安全に移動できることをコンパイラに明示的に通知しない限り、発生しません。

于 2012-01-17T00:45:38.953 に答える