4

私はboost::weak_ptrを使用してオブジェクトのプールを実装し、誰もオブジェクトの1つを使用していないときにそれらが刈り取られるようにすることを考えています。ただし、私の懸念は、これがマルチスレッド環境であり、スコープ外のオブジェクトに対する最後のshared_ptrと、weak_ptrから構築されている新しいshared_ptrとの間に競合状態があるようです。通常、このような操作はロックなどで保護します。ただし、ここで重要なのは、shared_ptrがいつスコープ外になるかわからないということです。

boost::shared_ptrとboost::weak_ptrについて何か誤解していますか?そうでない場合、誰かが何をすべきかについて何か良い提案がありますか?

ありがとう。

アンドリュー

4

3 に答える 3

11

を使用するweak_ptrには、通常、それを使用してaを作成することにより、強力な参照を取得する必要がありますshared_ptr。この最後のステップはアトミックです。強力な参照を取得するか、bad_weak_ptr例外がスローされます。(または、を呼び出しlock()weak_ptr、強力な参照またはnullを取得します。)

例(lock();他のスタイルに適応するのに十分簡単):

void do_something(weak_ptr<foo> weak) {
    // Grab strong reference
    shared_ptr<foo> strong(weak.lock());
    if (strong) {
        // We now have a strong reference to use
    } else {
        // No strong references left; object already freed
    }
}
于 2010-01-29T07:04:40.950 に答える
3

スレッドセーフに関しては、両方ともboost::weak_ptr類似boost::shared_ptrしています。オブジェクトがどこかで破壊されるリスクがある場合、これらはスレッドセーフではありません。またはweak_ptrで参照されているオブジェクトがどこかで永続的に参照されている場合、useはリスクなしでptrsをboost::shared_ptr使用できます。shared/weak

ただし、ある操作でオブジェクトの最後の生きているインスタンスを逆参照する場合、その時点では、次の操作を実行できません。特に、内部で使用するため、別の操作にweak_ptr割り当てることはできません。また、結果が未定義であるため、ロックを使用することはできません。また、メソッドは役に立ちません。trueを返す可能性がありますが、コードの次の行で、オブジェクトはすでに期限切れになっている可能性があります。weak_ptrweak_ptrshared_ptrexpired()

于 2012-01-18T13:10:18.437 に答える
0

はい、そうです。ポインタへのアクセスに関しては、Boostはすべてを安全にする必要がありました。それは彼らのポイントの一部です。

ただし、最後のshared_ptrが消えてから次の共有を作成するまでに遅延が予想される場合は、nullポインターを取得します。(適切にチェックしている場合は、適切なフェイルケースが発生するはずです)。

しかし、無効なshared_ptrで終わることはできません

于 2010-01-29T07:10:15.793 に答える