7

ドキュメントや他QObject多くの人が説明しているように、 aはQObjectアイデンティティを持っているため、コピーコンストラクタと代入演算子を隠しています。

QObjectただし、動的プロパティ機能またはシグナル/スロット機能から派生したものではありません。リフレクション、または にアクセスする機能のみが必要ですFoo::staticMetaObject

class Foo : public QObject {
    Q_OBJECT
    Q_ENUMS(Color)
public:
    enum Color { Blue, Red, Pink };
private:
    Color color;
};

Q_DECLARE_METATYPE(Foo::Color)

私はそれからコピーできませんFoo

Foo a;
Foo b;
a = b;

この場合、コピーと割り当てを許可する最善の方法は何ですか? コピー コンストラクターと代入演算子を必ず記述する必要がありますか? 彼らはどのように見えるでしょうか?リフレクションは機能しますか?

4

3 に答える 3

14

あなたがのための反射を持つことにのみ興味があるなら

  • クラス名、
  • 列挙型とフラグ(Q_ENUMS、Q_FLAGS)、
  • クラス情報(Q_CLASSINFO)、

Q_GADGET代わりにQ_OBJECT使用できます:

class Foo {
    Q_GADGET
    Q_ENUMS(Color)
public:
    enum Color { Blue, Red, Pink };
private:
    Color color;
};

を宣言して定義しますFoo::staticMetaObject

于 2011-08-26T02:12:45.233 に答える
2

派生クラスにコピー コンストラクターとコピー代入演算子の両方を確実に実装できますが、これは設計が悪いことを示している可能性があります。次の例を見てください。

#include <iostream>

class Base {
public:
    Base() {}

private:
    Base(const Base& other) {
        std::cout << "Base copy constructor invoked!" << std::endl;
    }
};

class Derived : public Base {
public:
    Derived() {}

    Derived(const Derived& other) {
        std::cout << "Derived copy constructor invoked!" << std::endl;
    }
};

int main(int argc, char** argv) {
    Derived a;
    Derived b = a;

    return 0;
}

これは問題なくコンパイルされます。ただし、予想どおり、結果のプログラムを実行すると、出力されるのはDerived copy constructor invoked!. 基本クラスがそのコピー コンストラクター/コピー代入演算子をプライベートとして宣言しても、派生クラスが独自のバージョンを実装することは妨げられません。派生クラスが基本クラスのバージョンを呼び出さないようにするだけです。

ここに問題があります。オブジェクトのすべての部分を確実にコピーして、実際に 2 つの別個のコピーを作成することをお勧めします。オブジェクトの一部には基本クラスが所有するデータが含まれているため、基本クラスのコピー コンストラクター/コピー代入演算子を呼び出して、完全なコピーが確実に作成されるようにする必要があります。しかし、そのデータは設計上、コピーできません。したがって、オブジェクトのすべての部分をコピーすることは不可能です。

このデザインを使い続けるかどうかはあなた次第です。自問すべき重要なことの 1 つは、派生クラスが本当にコピー可能である必要があるかということです。そうでない場合は、心配する必要はありません。

于 2011-08-26T00:21:52.390 に答える
1

についてはよくわかりませんqtが、コピーコンストラクターが許可されていない場合は、その理由があるはずです(投稿したリンクで説明されています)。これを持たないようにデザインを変更することができます。

それでもあなたが主張するなら、それmemcpyはあなたの最後の手段になる可能性があります. 個人的にはお勧めしません。ディープ コピーや vtable など、必ずしも些細なことではないことに注意する必要があるからです。

于 2011-07-23T06:15:27.180 に答える