3

私はstd::unique_ptr例えばを使い始めました:

unique_ptr<TFile> myfile( TFile::Open("myfile.root") );

それ以外の

TFile * myoldfile = TFile::Open("myoldfile.root") ;

今、自分の関数がどのように見えるべきかわかりません。問題の一部は、問題が明らかになるほどコードがまだ複雑ではないことかもしれませんが、物事がより複雑になったときに混乱しないように、今すぐ取得したいと思います。

私はかつて持っていた:

double interestingResult( TFile * input )
{...}

(これは実際には TFile を変更しませんが、TFile の一部の非 const 関数を呼び出すため、const にすることはできません)。

私はまだこれを呼び出すことができます:

myResult  = interestingResult( myfile.get() );

これはあまりユーザーフレンドリーではないようです。(ここで提案されていると思います: https://stackoverflow.com/a/5325560/1527126。)

または、関数を次のように変更できます。

double interestingResult( unique_ptr<TFile>& input )
{...}

これにより、ユーザーは常に unique_ptr を使用することになります。

または、次のように書くことで両方をサポートできます。

double interestingResult( unique_ptr<TFile>& input )
{ return interestingResult( intput.get() ); }

しかし、他の人のコードではそれが見られません。

この状況に対する標準的なアプローチは何ですか?

この回答( https://stackoverflow.com/a/9700189/1527126myfile )は、nullになるとは思わないため、参照を受け入れる必要があることを意味していると思います。しかし、ライブラリ関数TFile::Openは常にポインターを返すため、追加の逆参照なしで直接関数に渡すことができるのは当然のようです。

申し訳ありませんが、私は StackOverflow または CodeReview で質問する必要があるかどうかを判断することをあきらめましたが、そうでない場合は適切な場所を教えてください。

4

4 に答える 4

4

あなたが言及している答えは正しいものです。

既存のTFileインスタンスで動作する関数があり、有効な引数として NULL ポインターを受け入れる理由がなく、関数の引数が所有権を持たない場合は、TFile&as parameter type (TFile const&可能な場合) を使用する必要があります。渡されるオブジェクトが呼び出し元によって (所有権の有無にかかわらず) ポインターによって保持されていることは、その関数に違いをもたらすべきではありません。

引数の使用を選択することもできますがTFile *、NULL を渡すことの有効性について少なくともあいまいさが生じるため、将来的に問題が発生する可能性があります。

引数を使用する場合unique_ptr<TFile>は、オブジェクトの所有権を関数に完全に渡します。呼び出しが戻ると、呼び出し元には NULL が残されunique_ptrます。

引数を使用するunique_ptr<TFile>&場合、これは、関数がオブジェクトの所有権を引き継ぐか、呼び出し元に任せるかを選択できることを示します。むしろ珍しい。

引数はのunique_ptr<TFile> const&ように使用できますがTFile *、呼び出し元はオブジェクトを所有し、 を使用して管理する必要がありunique_ptrます。なぜそのような要件を発信者に課す必要があるのでしょうか? もちろん、これ (および の他の使用unique_ptr法) もすべて NULL ケースを処理する必要があります。

于 2013-03-13T16:43:01.517 に答える
3

パラメーター リストでスマート ポインターを受け入れる場合の問題は、呼び出し元が使用できるスマート ポインターの種類を指定することです。たとえば、unique_ptr を使用すると、呼び出し元が代わりに shared_ptr を使用できなくなります。

あなたの場合、参照パラメーターをお勧めします。また、通常のポインタもよく使用されています。主なことは、関数が戻り後に参照を保持したり、オブジェクトの所有権を取得したりしようとしないことです。つまり、後でメモリを解放する責任はありません。

于 2013-03-13T16:39:35.337 に答える
2

参照TFile &でもポインタでも構いませTFile *ん。

null ポインターが関数への無効な入力である場合、参照を使用する必要があると言う人がいます。std::strlenこれらの人々は、C から継承された などの標準関数を使用しようとすると、混乱して怒ってしまいますstd::memcpy。リファランドが必要な自己文書への参照を使用することは非常に良いことですが、API を使用することも非常に良いことです。参照と一貫して動作するか、ポインターと一貫して動作します。

const 以外の参照パラメーターを使用して「すべきではない」と言う人がいて、ポインターを優先します。のような標準関数を使用しようとすると、混乱して怒ってしまいますstd::swap。これは、C プログラマーにとって値渡しのように見え、入力を変更する「べきではない」ためです。

そのどちらとも一緒に仕事をしない限り、自分で選択することができます。

于 2013-03-13T16:53:38.400 に答える
1

それは異なりますが、関数はポインターの所有権を取得しないため、関数で生のポインター (またはオブジェクトへの参照) を使用することをお勧めします。

また、ある日、 を使用することにした場合はshared_ptr...

于 2013-03-13T16:41:03.750 に答える