2016-09-04 24 views
1

エイリアス共有ポインタの管理対象オブジェクトを取得しようとしています。私の考えは弱いポインタを使用していた。弱ポインタ​​はオブジェクトを生成しないので、共有ポインタから弱ポインタ​​を作成すると、弱ポインタ​​はエイリアス共有ポインタの格納オブジェクトを忘れて弱ポインタ​​をロックすると、ポインタ。しかし、私が得た結果は私を混乱させます。ウィークポインタは、どの共有ポインタが構築されているかを覚えていますか?エイリアス共有ポインタの管理対象オブジェクトを取得する方法はありますか?スマートポインタの予期しない動作

template<class T> struct Deleter { 
    void operator()(T* p) const {}; 
}; 

Deleter<T> d {}; 
T t1 {}; 
T* p1 = &t1; 
T t2 {}; 
T* p2 = &t2; 
auto sp1 = std::shared_ptr<T>(p1,d); 
auto sp2 = std::shared_ptr<T>(sp1,p2); 
auto wp = std::weak_ptr<T>(sp2); 
std::cout << sp1.get() << " " << sp2.get() << " " << wp.lock().get() << std::endl; 

農産物0x7fff5798c958 0x7fff5798c948 0x7fff5798c948

+3

どうしたのですか?どのような異なる出力を期待していましたか? – Barry

+0

私は '0x7fff5798c958 0x7fff5798c948 0x7fff5798c958'を期待しました –

+0

' shared_ptr'と 'weak_ptr'が期待通りの動作をするのは非常に悪いことでしょう。 'shared_ptr'のエイリアシングはそれほど有用ではありません。 – StoryTeller

答えて

1

弱いポインタが構築されているものを共有ポインタから覚えていますか?

shared_ptrによって格納された生ポインタを覚えています。あなたが期待しているように物事がうまくいくなら、それは非常に混乱していると思います。たとえば、関数が引数としてshared_ptr<T>を受信した場合、エイリアスかどうかはわかりません。そして、その機能がshared_ptrからweak_ptrを取りたいと思ったら、それはshared_ptrとの全く異なるオブジェクトを与えたweak_ptrへのweak_ptrのそれが得られたことを見いだすことは非常に驚くべき振る舞いであると思います。

エイリアシングshared_ptrには、エイリアシングであるshared_ptrとは異なるタイプを保存できます。タイプは互いに交換可能である必要はありません。そして、エイリアシングshared_ptrから構築されたweak_ptrは、それが構築されたshared_ptr(または暗黙的に変換可能なタイプ)からその格納されたタイプを取得します。

エイリアシングの最も一般的な使用例shared_ptr(私には一度も必要がなかったにしても)が疑わしいですが、共有オブジェクトのメンバーを渡して、それが生きていることを確実にすることです残りの所有オブジェクトがもはや必要でない場合したがって、あなたが作成したシナリオでは、エイリアシングのタイプが元のものと同じであることが珍しいと思われます。shared_ptr

エイリアス共有ポインタの管理対象オブジェクトを取得する方法はありますか?

私が知っている限り、いいえ。おそらくそこにあるはずです。この機能が役立つと思うなら、それを提案してください。 https://groups.google.com/a/isocpp.org/forum/?fromgroups#!forum/std-proposals

+0

ありがとうございます。私が提示したシナリオは、管理対象オブジェクトを生成するためにエイリアス化された共有ポインタを欺くために作られました。私はちょうどそれがこの機能性を欠くことに驚いていた。しかしそれには十分な理由があるかもしれません。 –

+0

@JiříLechner:私は、その機能性が欠けている唯一の理由は誰もそれを考えていなかったと考えています。誰もそれを必要としなかったので誰もそれを考えなかったと思う。あなたがそれを必要とする場合は、ユースケースを完成させ、私の答えの一番下にリンクしているフォーラムに投稿してください。 –