1

次のコードがあります。

void Stack::operator =(Stack &rhs)
{
    //do the actual copying
}

Stack::Stack(Stack &rhs) //copy-constructor
{
    top=NULL; //initialize this as an empty stack (which it is)
    *this=rhs; //invoke assignment operator
}

Stack& Stack::CopyStack()
{
    return *this; //this statement will invoke copy contructor
}

次のように使用されています。

unsigned Stack::count()
{
    unsigned c=0;
    Stack copy=CopyStack();
    while (!copy.empty())
    {
        copy.pop();
        c++;
    }
    return c;
}

CopyStack の宣言から参照シンボルを削除しても (参照ではなくコピーを返す)、Visual Studio 2008 では違いがありません (コピーが呼び出される回数に関して)。私はそれが最適化されていると思います-通常、最初に戻り値のコピーを作成し、次に割り当て演算子をもう一度呼び出して変数scに割り当てます。

さまざまなコンパイラでのこの種の最適化について、どのような経験がありますか?

よろしく、 ジェナン

4

3 に答える 3

2

このステートメントは、 の戻り値からStack呼び出された のコピー初期化です。課題はありません。copyCopyStack()

Stack copy=CopyStack();

この関数では、コメントが正しくありません。戻り値は参照であるため、コピー コンストラクターの呼び出しはありません。

Stack& Stack::CopyStack()
{
    return *this; //this statement will invoke copy contructor
}

これは、元の初期化が事実上、*this変数からのコピー構築であることを意味します。

戻り値が値によるものである場合、コピーの初期化は一時的なものになりますが、コンパイラによって有効に削除される可能性があります。

関数のポイントがわかりませんCopyStack。直接初期化を実行する方がより慣用的です。

Stack copy(*this);
于 2010-04-03T15:18:24.983 に答える
0

私の理解が正しければ、スタック オブジェクトのプロトタイプを作成し、代わりにプロトタイプを返すことができます。これにより、パフォーマンスが向上する可能性がありますが、メモリ リソースのオブジェクト所有権について注意する必要があります。

必要に応じて、Prototype Factory のデザイン パターンを使用できます。

于 2010-04-03T16:16:11.257 に答える
0

あなたが探しているのは、RVO (戻り値の最適化) と NRVO (名前付きの戻り値の最適化) だと思います。コンパイラの最適化は広大な主題であり、説明を入力し始めると、非常に時間がかかります! このブログ投稿をチェックしてください...うまく説明しています。

于 2010-04-03T16:17:47.757 に答える