How to cast QSharedDataPointer
-
Hi !
How to dynamic_cast a QSharedDataPointer<Base> object into a QSharedDataPointer<Derived> object whitout loosing the reference counting from the Base object ?
NB: Base inherits QSharedData.
NB: Derived inherits Base. -
Can u have a look at "QSharedDataPointer sample":http://cdumez.blogspot.pt/2011/03/implicit-explicit-data-sharing-with-qt.html
Hope this helps ;)
-
[quote author="bjanuario" date="1370715462"]Can u have a look at "QSharedDataPointer sample":http://cdumez.blogspot.pt/2011/03/implicit-explicit-data-sharing-with-qt.html
Hope this helps ;)[/quote]
It doesn't. There's nothing in that article about polymorphism or dynamic casting.
I'm also interested in this question. Does anyone have a good solution?
-
I've thought about this a bit and think I may have a solution. The idea is that only the base class contains a QSharedDataPointer and the derived classes access it via static_cast. It's essentially a form of static polymorphism. Here's the code:
@
class BaseDataType
{
const char* getter() const;
void setter(const char*);
};class DerivedDataType
{
const char* getter_derived() const;
void setter_derived(const char*);
};class BaseData : public QSharedData
{
public:
// the standard ctor and copy ctor go here// my data is a pointer to a polymorphic type
BaseDataType* ptr;
};class Base
{
public:
// the standard ctor and copy ctor go hereprotected:
// subclasses use this to access the shared ptr and then static cast it
QSharedDataPointer<BaseData> real_d;
};class Derived
{
public:
// ctor and copy ctor go hereconst char* getter_derived() const
{
// const access - won't cause a detach
return d()->getter_derived();
}void setter_derived(const char* str)
{
// non-const access - may cause a detach
d()->setter_derived(str);
}private:
// these accessors replace the standard "d" pointer:// the -> won't cause a detach here
const DerivedDataType* d() const {return static_cast<DerivedDataType*>(real_d->ptr);// the -> may cause a detach here
DerivedDataType* d() {return static_cast<DerivedDataType*>(real_d->ptr);}};
@This only just occured to me, so somebody please let me know if I'm missing something.