2

クラスのメンバーとして boost::shared_ptr を使用して実装する最もクリーンな方法を見つけようとしています。クラス B メンバーへの boost::shared_ptr を含むクラス A があるとします。B クラスは、基本型 (B) または派生型 (C または D としましょう) のいずれかです。このメンバーは、クラス A の存続期間中 (アクセサー/修飾子を使用して) 継続的に取得/設定されます。B はポリモーフィックでなければならないので、単に B として保存するのではなく、B への参照/ポインターとして保存することはできません。また、自分でメモリを管理する必要も避けたかったのです。すべてが次のように見えたとしましょう:

class A
{
public:
    const B& GetB() const { const B* b = m_pB.get(); return *b; } // Is the correct way to do this?
    void SetB(const B& b) { B* b = m_pB.get(); *b = b; } // Is the correct way to do this?

private:
    boost::shared_ptr<B> m_pB;
};

私はおそらく何か間違ったことをしていることを知っていますが、私が達成しようとしていることの例を提供したいと思いました. ありがとう!

4

2 に答える 2

1

このプログラムの設計は再考する必要があると思います。

共有ポインターの目的は、動的に割り当てられたリソースをその中に残して、そのリソースのライフサイクルを管理することです。そこにあるものを変更している場合、そこにあるポインターを置き換えた後、そのリソースの寿命を管理する責任があり、混乱につながります。

おそらく、m_pB 変数に新しい共有ポインターを割り当てるだけで、元のポインターがスコープ外になり、最初に保持されていたリソースが解放されるはずです。そのため、保持しているポインターではなく、共有ポインターを割り当てます。

于 2012-08-10T14:48:33.130 に答える
0

セッターでは、ポインターを更新するのではなく、新しいデータを既存の要素に割り当てています。

正しい方法は次のとおりです。

void SetB(shared_ptr<B> ptr)
{
     m_pB = ptr;
}

これを行うと、オブジェクトの所有権をクラスに移すことになります。使用するには、次のようなコードを記述します。

A a;

shared_ptr<B> ptrB(new C()); //or new D, whatever
a.SetB(ptrB);

B を作成するコードが shared_ptr をまったく使用せず、shared_ptr がクラス内にカプセル化される場合の別のオプションは、セッターを変更して B へのポインターを取得することです。

void SetB(B *pB)
{
     m_pB.reset(pB);
}

最後に、この最後のサンプルが必要であり、shared_ptr がクラス A のみに制限される場合、shared_ptr の代わりに scoped_ptr を使用することをお勧めします。

于 2012-08-10T14:52:29.920 に答える