[Development] parented_ptr

A. Pönitz apoenitz at t-online.de
Wed Nov 5 18:49:00 CET 2025


On Wed, Nov 05, 2025 at 12:05:49PM +0000, Volker Hilsheimer via Development wrote:
> 
> > On 5 Nov 2025, at 12:30, Ville Voutilainen <ville.voutilainen at gmail.com> wrote:
> > 
> > On Wed, 5 Nov 2025 at 12:11, Volker Hilsheimer via Development
> > <development at qt-project.org> wrote:
> >> And again, we need to make sure that object->createChild<QWidget>() is not possible; from what I see, that can be solved via SFINAE:
> >> 
> >> class QObject …
> >> {
> >>    template <typename ChildType, typename ...Args,
> >>              std::enable_if_t<!std::is_base_of_v<QWidget, ChildType>, bool> = true
> >>> 
> >>    ChildType *makeChild(Args &&...args)
> >>    {
> >>        return new ChildType(std::forward<Args>(args)..., this);
> >>    }
> >> };
> >> 
> >> (it’s enough for QWidget to be forward declared, which it is already in qobject.h)
> >> 
> >> and then overloading this in QWidget without the constraint (a QObject can be a child of a QWidget).
> > 
> > I don't quite follow why you think you need any SFINAE for this. If
> > you try to construct a QWidget child with a
> > QObject::createChildObject(),
> > that will fail to compile anyway because it tries to pass a QObject*
> > parent to the QWidget constructor, and that
> > constructor takes a QWidget*. There is no implicit base*->derived* conversion.
> 
> 
> “fails to compile” != “fails to compile and produces a meaningful error message”
> 
> 
> Without SFINAE:
> 
> [... 6 ugly lines ....]
> 
> With SFINAE:
> 
> /Users/vohi/qt/dev/qtbase/tests/auto/widgets/kernel/qwidget/tst_qwidget.cpp:14209:12: error: no matching member function for call to 'makeChild'
>  14209 |     object.makeChild<QLineEdit>();
>        |     ~~~~~~~^~~~~~~~~~~~~~~~~~~~
> /Users/vohi/qt/dev/qtbase/src/corelib/kernel/qobject.h:354:16: note: candidate template ignored: requirement '!std::is_base_of_v<QWidget, QLineEdit>' was not satisfied [with ChildType = QLineEdit, Args = <>]
>   354 |     ChildType *makeChild(Args &&...args)

I appreciate that this is moving from 'makeFooChild' to 'makeChild' and consequently
makes the user code not unbearably longer than the original.

It also looks good enough to me to teach to tools with peladophobia in order to reduce
their anxiety level without the need to invent the tr("drölfzigsten") smart pointer.

To me this looks like a winner.

Andre'


More information about the Development mailing list