7

私はこのアイテムに似た何かをしています正しいBOOST_FOREACHの使用法?

ただし、返されたリストはboost::shared_ptrでラップされています。BOOST_FOREACHループの前にリストを変数に割り当てないと、リストが一時的なものであるためにリストが破棄されるため、実行時にクラッシュします。

boost::shared_ptr< list<int> > GetList()
{
    boost::shared_ptr< list<int> > myList( new list<int>() );
    myList->push_back( 3 );
    myList->push_back( 4 );
    return myList;
}

じゃあ後で..

// Works if I comment out the next line and iterate over myList instead
// boost::shared_ptr< list<int> > myList = GetList();

BOOST_FOREACH( int i, *GetList() ) // Otherwise crashes here
{
    cout << i << endl;
}

変数「myList」を導入せずに上記を使用できるようにしたいと思います。これは可能ですか?

4

2 に答える 2

2

わかりました、shared_ptr の「ベスト プラクティス」では、名前のない一時変数の使用を避けるように言及されています。

http://www.boost.org/doc/libs/release/libs/smart_ptr/shared_ptr.htm#BestPractices

入力を節約するために、名前のない shared_ptr 一時変数を使用しないでください。これが危険な理由を確認するには、次の例を検討してください。

void f(shared_ptr<int>, int); int g();

void ok() {
    shared_ptr<int> p(new int(2));
    f(p, g()); }

void bad() {
    f(shared_ptr<int>(new int(2)), g()); }

関数 ok は文字どおりガイドラインに従いますが、bad は一時的な shared_ptr を所定の場所に構築し、メモリ リークの可能性を認めます。関数の引数は指定されていない順序で評価されるため、new int(2) が最初に評価され、g() が 2 番目に評価される可能性があり、g が例外をスローした場合、shared_ptr コンストラクターに到達しない可能性があります。

上記の例外の安全性の問題は、boost/make_shared.hpp で定義されている make_shared または allocate_shared ファクトリ関数を使用することによっても解消される場合があります。これらのファクトリ関数は、割り当てを統合することによって効率の利点も提供します。

于 2011-07-04T19:24:41.547 に答える
0

以下を使用する必要があります。

T* boost::shared_ptr<T>::get()

例:

BOOST_FOREACH( int i, static_cast< list<int> >( *(GetList().get()) ) ) {

}

問題は、boost::shared_ptr を逆参照できず、格納されている基になるオブジェクトが返されることを期待できないことです。これが真である場合、boost::shared_ptr へのポインターを逆参照する方法はありません。特別な ::get() メソッドを使用して、boost::shared_ptr によって格納されたオブジェクトを返し、それを逆参照する必要があります。

ドキュメントについては、http://www.boost.org/doc/libs/1_46_1/libs/smart_ptr/shared_ptr.htm#getを参照してください。

于 2011-07-04T16:04:52.130 に答える