Incomplete types and intrusive_ptr
Is it possible to achieve the ability of shared_ptr<T> to be used as a class member in a class declaration with an incomplete type T, with intrusive_ptr? For new code, I'm wrapping classes in shared_ptr, instead of deriving from our refcounted base class. I've also started to use intrusive_ptr for all the legacy code that already derives from RefCountedBase, but unlike shared_ptr I'm forced to #include the header for the type wrapped in the intrusive_ptr, something I'd like to avoid, to reduce build times. Isn't it possible to have a mix of shared_ptr and intrusive_ptr which also captures a Destructor instance when the intrusive_ptr is assigned, similarly to what shared_ptr does? Has this been considered before? Thanks, --DD PS: We have full control of RefCountedBase, so would refactoring it to use boost::detail::shared_count internally allow the change I discuss above? If so, how would one go about it?
Dominique Devienne:
Is it possible to achieve the ability of shared_ptr<T> to be used as a class member in a class declaration with an incomplete type T, with intrusive_ptr?
The usual approach is to declare: class X; void inrisuve_ptr_add_ref( X* ); void intrusive_ptr_release( X* );
On Tue, May 12, 2009 at 3:11 PM, Peter Dimov
Dominique Devienne:
Is it possible to achieve the ability of shared_ptr<T> to be used as a class member in a class declaration with an incomplete type T, with intrusive_ptr?
The usual approach is to declare:
class X; void intrusive_ptr_add_ref( X* ); void intrusive_ptr_release( X* );
Thanks Peter. This helped me see that I need a declaration of the
add_ref/release functions *per* derived class T of RefCountedBase,
that I want to fwd declare to avoid including its header.
Previously I just declared add_ref/release for RefCountedBase, and
since the derivation is not know by just fwd decl SomeRefCounted, I
was getting this error:
error C2664: 'boost::intrusive_ptr_release' : cannot convert parameter
1 from 'acme::SomeRefCounted *' to 'acme::RefCountedBase *'
and wrongly assumed intrusive_ptr<T> required a complete T. I've
summarized the issue I was having below. Thanks again for your help.
Regards, --DD
// in refcountedbase.h
namespace acme {
class RefCountedBase {
public:
void ref() { ++refcount_; }
void unref() { if (--refcount_ == 0) { cleanup(); delete this; } }
static void ref(RefCountedBase* r) { if (r) r->ref(); }
static void unref(RefCountedBase* r) { if (r) r->unref(); }
protected:
RefCountedBase() : refcount_(0) {}
RefCountedBase(const RefCountedBase&) : refcount_(0) {}
virtual ~RefCountedBase() {}
virtual void cleanup() {}
private:
RefCountedBase& operator=(const RefCountedBase&);
private:
int refcount_;
};
}
// in acme/intrusive_ptr.h
#include
participants (2)
-
Dominique Devienne
-
Peter Dimov