|
Boost : |
From: Peter Dimov (pdimov_at_[hidden])
Date: 2007-03-01 14:09:09
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
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk