Boost logo

Boost :

From: Peter Dimov (pdimov_at_[hidden])
Date: 2004-10-28 07:19:40


Oleg Fedtchenko wrote:
> But the owner may be not an immediate
> class-container-of-the-member or its derivative but any
> arbitrary class like this:
>
> class A
> {
> public:
> WORD m_wData;
> };
>
> class B
> {
> public:
> A a;
>
> friend shared_ptr<WORD> GetData( shared_ptr<B> this_ )
> {
> return shared_ptr<WORD>(
> &this_->a.m_wData,
> boost::bind( &shared_ptr<A>::reset, this_ )
> );
> }
> };
>
> In this case we must create overridden functions for every
> owner type to correctly specify pointer to a member.

Yes.

> And what about when A::m_wData is private?

Well, it depends on the actual level of privacy. Clearly a member whose
address is always exposed to the world isn't really private, regardless of
its access specifier.

But that aside, depending on the level of coupling between A and B, B should
either be a friend of A, or it must go via an analogous mechanism to obtain
WORD* from A*:

// in A
friend shared_ptr<WORD> GetData( shared_ptr<A> this_ )
{
     return shared_ptr<WORD>(
         &this_->m_wData,
         boost::bind( &shared_ptr<A>::reset, this_ )
     );
}

// in B
friend shared_ptr<WORD> GetData( shared_ptr<B> this_ )
{
     shared_ptr<A> pa( &this_->a,
         boost::bind( &shared_ptr<B>::reset, this_ ) );

     return GetData( pa );
}

Yes, this is not very efficient. But it's encapsulated (which is pretty much
the only point of making the data members "private" in this case.) That is,
you can change B::a from

    A a;

to

    shared_ptr<A> pa;

without changing the client code, or you could even generate the A
dynamically inside GetData. Similarly, you can change A::m_wData to
shared_ptr<WORD>.

Another shared_ptr advantage is that weak_ptr works.

> Don't you think this is the better variant:
>
> template<class Z>
> shared_ptr<WORD> A::GetData( shared_ptr<Z> owner )
> {
> return shared_ptr<WORD>(
> &m_wData,
> boost::bind( &shared_ptr<Z>::reset, owner )
> );
> }

This is error-prone. I can pass any shared_ptr as an owner, regardless of
whether it actually owns *this.


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk