2011-11-15 7 views
0

への参照を返すことは、このコードを見てみましょう:オブジェクトコンストラクタ

Foo &Bar::Copy() 
{ 
    return Bar(); 
} 

クラスのバーはFooのから継承され、fooは抽象クラスです。しかし、私がBar()と呼んでそれを返すと、それは安全ですか?または、Copy()関数の終了時に解放されるローカル変数のアドレスを返すでしょうか?

アドバイスをいただければ幸いです!

+0

[C++ローカル変数への参照を返す]複製可能です。http://stackoverflow.com/questions/4643713/c-returning-reference-to-local-variable – GWW

+0

@GWW - そうではありません。ローカル割り当てを返すかどうかを数えるコンストラクタを返すかどうかはわかりませんでした。同じことについて混乱している人にとっては、おそらく有益でしょう。 – AutoBotAM

+0

実際には、rvalueが非const参照にバインドされているため、これはコンパイルすべきではありません。 – celtschk

答えて

1

Bar();を呼び出すときは、参照が返される暗黙的な一時オブジェクトに対してコンストラクターを呼び出します。 Clone()のような関数を作成する場合、典型的な解決策はヒープ上にクローンをnewで作成することです。ライフサイクル管理を簡素化するために、一種のスマートポインタを使用できます。また、共変リターン型を適用して、型変換を避けることもできます。Bar &Bar::Copy()

0

一時的なBarオブジェクトが;で破棄されるため、これは未定義の動作です。

Foo Bar::Copy() 
{ 
    return Bar(); 
} 

はより安全です。しかし@Cat Plus Plusと@celtschkのおかげで、この方法はスライスにつながり、すべてBarの特定の情報が失われることに気付きました。 Barオブジェクトを維持するためには、Copy()は参照またはオブジェクトへのポインタを返す必要があります。これがUBのようにここに再び始まります。だからBarは、代わりに動的に割り振られなければならず、参照/ポインタはCopy()関数の外に存在する。この動的に生成されたBarオブジェクトを削除する責任は誰にありますか?

#include <memory> 
std::shared_ptr<Foo> Bar::Copy() 
{ 
    return std::shared_ptr(new Bar()); 
} 

shared_ptrが自動的にこれを行います。

+2

2番目のスニペットはオブジェクトをスライスします。 –

+0

最初のスニペットはオブジェクトもスライスします。 – celtschk

+0

@CatPlusPlus:ありがとう、答えを編集しました。 –

1

あなたはctorを返していません。 Bar();は、を呼び出して一時オブジェクトを作成します。その後、その一時オブジェクトへの参照を返します。

C++のctorには名前がないので、関数へのポインタの取得や返すなど、通常の関数ではできることはほとんどありません。ここで本当に達成しようとしていることは完全にはっきりしませんが、オブジェクトを作成するものを返す場合は、通常はctorを呼び出す静的メンバー関数を定義し、その静的メンバー関数へのポインタを返す必要があります。

+0

長期的には、私は 'Foo *'ポインタの配列を作成しようとしています(理論的には、実際のプログラムではFooと呼ばれていません)。私はポインタの寿命がそれに挿入されていると心配していたので、定義されていない振る舞いになりやすいので、アドレスの寿命が配列と結びつくようにコピーを挿入しようとしていました。私はスマートなポインタを使用して、ヒープに割り当てることは、jszpilewskiが言及したように、これには最善の方法だと思います。 – AutoBotAM

+0

@AutoBotAM:Boost [ptr_vector](http://www.boost.org/doc/libs/1_48_0/libs/ptr_container/doc/ptr_vector.html)もご覧ください。 –

+0

ポインタコンテナライブラリは、すべて私が必要とするように見えます。しようとします。 – AutoBotAM

関連する問題