0

注: この質問は前の質問に続きます。新しい質問として引き続き質問しても問題ないことを願っています。

次のようなツリー クラスの「3.5 ビッグ ルール」(コピー アンド スワップ イディオム) を実装しようとしています。

class Tree
{
    friend void swap(Tree &first, Tree &second); // Swap function

public:
    Tree(const double &a, const double &b, int depth); // Public constructor (derived from the default (private) constructor)
    Tree(const Tree &other); // Copy constructor
    ~Tree(); // Destructor
    Tree & operator=(Tree other); // Copy-assignement operator


private:        
    Tree(double *a, double *b, int depth, int maxDepth); // Default (private) constructor

    double *a, *b;
    int depth, maxDepth;    
    Tree *leftChild, *rightChild;
};

私はこのガイドラインに従うように努めてきました。私のコピー代入演算子は次のようになります。

Tree & Tree::operator=(Tree other)
{
    swap(*this, other);
    return *this;
}

パブリックコンストラクターを機能させるのに苦労しています。誰かが私に次のようなことを提案しました:

Tree::Tree(const double &a, const double &b, int depth)
{
    double aTemp(a), bTemp(b);
    swap(*this, Tree(&aTemp, &bTemp, depth, depth));
}

このアイデアが機能するかどうかはわかりません。いずれにせよ、コンパイラから次のエラーが表示されます。

invalid initialization of non-const reference of type 'Tree&' from an rvalue of type 'Tree'
in passing argument 2 of 'void swap(Tree&, Tree&)'

代わりに、次のアイデアを試しました。これはうまくいくと思いました。

Tree::Tree(const double &a, const double &b, int depth)
{
    double aTemp(a), bTemp(b);
    *this = Tree(&aTemp, &bTemp, depth, depth);
}

しかし、それも機能していないようです。*this = Tree(&aTemp, &bTemp, depth, depth)問題は、コピー代入演算子( )を呼び出すときにコピーコンストラクターを呼び出す必要があることだと思います(コピー代入演算子の引数は値渡しであるため)が、これが行われていないようです。私はなぜなのか理解していない。

助けてくれてありがとう!

4

1 に答える 1

1

'void swap(Tree&, Tree&)' の引数 2 を渡す際に、タイプ 'Tree' の右辺値からのタイプ 'Tree&' の非 const 参照の無効な初期化

constC++ では、無名オブジェクトを非参照で渡すことはできません。その目的は、参照引数に書き込む関数の結果を呼び出し元が誤って破棄するのを防ぐことです。

代わりに次のことができます。

Tree::Tree(const double &a, const double &b, int depth)
{
    double aTemp(a), bTemp(b);
    Tree temp(&aTemp, &bTemp, depth, depth);
    swap(*this, temp);
}

しかし、それも機能していないようです。問題は、コピー代入演算子 (*this = Tree(&aTemp, &bTemp, depth, depth)) を呼び出すときに、コピー コンストラクターを呼び出す必要があることだと思います (コピー代入演算子の引数は値で渡されるため) )、しかし、これは起こっていないようです。私はなぜなのか理解していない。

それが機能していないことをどのように判断していますか?コンパイラは、不要な作業を避けるためにコピーを除外する場合があります。(これが、コピー代入演算子が引数を値で受け取る理由です。 )

ところで、コンパイラが C++11 をサポートしている場合は、代わりに委譲コンストラクタを使用できます。

于 2013-08-09T05:06:18.630 に答える