[Development] Don't use Private *d when your class is immutable

Marc Mutz marc.mutz at kdab.com
Fri Mar 3 13:57:56 CET 2017


On Friday 03 March 2017 13:37:36 Olivier Goffart wrote:
> On Freitag, 3. März 2017 12:19:42 CET Marc Mutz wrote:
> > But don't - ever- use ref-counting on immutable classes. It's not easier
> > (you need to implement all the special member functions, which peoole, me
> > included[1][2], get wrong more often than we dare to admit).
> 
> refcounting is easy:
> 
> 
> class FooBarPrivate;
> class FooBar {
> public:
>     QString someGetter();
>     QString someOtherGetter();
>     FooBar(QString something, QString somethingElse);
> 
> private:
>     const QSharedPointer<const FooBarPrivate> d;
> };
> 
> And in the .cpp:
> class FooBarPrivate { /*...*/ };
> 
> FooBar::FooBar(QString a, QString b) :
> 	d(QSharedPointer<FooBarPrivate>::create(std::move(a), std::move(b)));
> {}
> 
> 
> What did i do wrong?

1. The class is the size of two void*s, which doubles the space requirements
   over what everyone assumes the size of a pimpled, non-polymorphic class to
   be (and makes the type unsuitable for QList).
2. The class is not assignable.
3. The class is not default-constructible (don't tell me it's by design;
   QVector cannot handle such types).
4. You forgot Q_DECLARE_SHARED (which requires member-swap())

And while *you* got it right, for most people we'd need to add:

5. You didn't use QSP::create()

Thanks,
Marc

-- 
Marc Mutz <marc.mutz at kdab.com> | Senior Software Engineer
KDAB (Deutschland) GmbH & Co.KG, a KDAB Group Company
Tel: +49-30-521325470
KDAB - The Qt, C++ and OpenGL Experts



More information about the Development mailing list