2

重複の可能性:
アクセサーは値または定数参照を返す必要がありますか?

まず第一に、セッターとゲッターは悪である/悪ではないことを無視しましょう。:)

std::私の質問は、メンバーとしてコンテナーを持つクラスがある場合string、ゲッターの戻り値の型はどうあるべきかということです。const T&パフォーマンス上の理由から、私はどちらかというと好きTです...ほとんどの場合、ユーザーはとにかくコピーを作成しますが、常にではないと思います。私が間違っている?

したがって、一般的に何が優れているか:

std::string get_name() const;

また

const std::string& get_name() const;
4

4 に答える 4

7

定数参照を返します。ユーザーがコピーを作成したい場合は、背中を剥がしてはいけません。

于 2012-09-30T23:37:54.147 に答える
2

考慮事項は次のとおりです。

1) コピーを返却しますstring。次に、ドキュメントは単純であり(「...の現在の値を返す」)、関数は遅いです(戻り値が...理論的には、コンパイラがstring副作用のないコピーを持つ値型として認識し、呼び出し元がコピーを使用している間は参照先が変更できないことを証明し、代わりに参照を使用することは可能です。しかし、それだけで十分でしょうか?)。

2) 参照を返しますconst string&。次に、ドキュメントは複雑です(「現在の値を含むオブジェクトへの参照を返しますstring...この参照は、次の時間まで有効です...その時間の次のサブセットに対して同じ値を含み続けます... 」)。呼び出し元がコピーを必要としない場合、関数は高速です。stringクラスの実装は、適切なライフタイムで返すものが何もないため、将来的に常にその文字列をデータメンバーとして格納するようにかなり制限されています。

エイリアシングは潜在的に高速ですが (コピーを回避する場合)、複雑です (参照元が変更または消失する可能性があるため)。そのため、参照を返す関数は潜在的に高速ですが複雑です。なお、(1)は「オブジェクトのプロパティを返すゲッター」ですが、(2)は「オブジェクトのprivateメンバーを返すゲッター」です。したがって、ゲッターが悪である場合、(2) は(1)よりも悪です。

他の密結合クラスがデータを取得するためのハックとしてゲッターが本質的に存在する場合、またはクラスがいつ変更されるかについて非常に明白なセマンティクスを持っている場合、たとえば「オブジェクト」、または文字列が非常に巨大であると予想される場合は、コピーを取得することめったになく、呼び出し元は値の動作ではなくビューの動作を期待するため、参照によって公開することが合理的です. 私が書いているクラスが明示的に「大きな文字列を保持し、X を実行する一方で、X を実行するもの」として明示的に設計されていない限り、安全のために、インターフェイスが永久に互換性があると想定されている場合は、おそらく値を返します。文字列が見えます」。

不変のガベージコレクションされた文字列は、この問題を解消します。これはおそらく、高水準言語の設計者にとって魅力的な理由の 1 つです。

于 2012-10-01T01:08:44.660 に答える
1

一般に、const 参照が理想的です。ケレックが言ったように、コピーが必要な場合は、自分で作成できます。これが潜在的に問題を引き起こす可能性がある唯一の場所は、完全に参照の受信者の責任です。たとえば、const 参照 var が、const 参照を返すオブジェクト メンバーの結果を受け取り、そのオブジェクトが後で参照変数の有効期間とは無関係に破棄される場合、事実上ポインターを「記憶」したことになります (大まかな用語)。それはもはや有効ではありません。すなわち:

const std::string& myref = myobj->getString();
...
delete myobj;

しかし、(コードを書いているのだから) これについての知識を持っている必要があり、最初からそれを避けるように計画する必要があります。参照を取得するのではなく、コピーを作成する必要がありますが、それでも参照を返すことをお勧めします

于 2012-09-30T23:46:13.267 に答える
1

それは、ゲッターの最も一般的な用途に依存します。

その文字列が取得操作の瞬間からプログラムの終了まで使用される場合、文字列の有効期間についてユーザーに「約束」したくないため、コピー操作をお勧めします。

その文字列が一時的に使用される場合は、参照を使用してください。

システム全体で何らかの文字列リポジトリを使用している場合、すべての文字列の有効期間が確実に把握されます。そのリポジトリから参照を安全に返すことができます。

于 2012-09-30T23:42:22.090 に答える