
Michael Anderson wrote:
Howdy everyone. I have some code that uses pointers to member variables that I want to switch to using boost::shared_ptrs, some of the code looks like this.
class Bar {}; class Foo { public: Bar bar; };
... Foo * fooptr = new Foo; Bar * barptr = &Foo.bar; ...
So to make this work with shared_ptrs I can do this:
class Bar {} class Foo { public: Foo() : bar(new Bar) {} shared_ptr<Bar> bar; };
... shared_ptr<Foo> fooptr(new Foo); shared_ptr<Bar> barptr = fooptr->bar; ...
But this means I have to change each of the classes... which is a bit ugly. Also it has unlinked the lifetime of the Bar and Foo objects.
So the solution I've come up with means that the Foo object only gets destroyed when both the barptr and the fooptr are destroyed. Unfortunately this requires additions to the shared_ptr class (the patch is below). The changes are _very_ similar to what is used for handling the pointer conversions and casts.
There has been a formal proposal to add an "aliasing constructor" (as in your patch, but public and without the tag) to std::tr1::shared_ptr and I'm considering adding one for 1.35. In the meantime,
+template<class T, class M> shared_ptr<M> member_pointer( shared_ptr<T> const & t, M* m) +{ + return shared_ptr<M>(t,m, detail::memberpointer_tag() ); +}
you can use: template<class T, class M> shared_ptr<M> member_pointer( shared_ptr<T> const & t, M* m) { return shared_ptr<M>( m, bind( &shared_ptr<T>::reset, t ) ); } A similar trick is described in: http://www.boost.org/libs/smart_ptr/sp_techniques.html#another_sp