❝继承于QObject并设置setParent即可获得半自动内存管理的能力。 ❞
QWidget *widget = new QWidget;
QPushButton *button = new QPushButton(w);
delete widget;
widget = NULL;
由于button对象的父对象是widget,则删除widget后会同时删除button的内存,并不再需要手动删除button对象的内存。 析构顺序:先析构QPushButton再析构QWidget。
当继承于QObject的对象使用了setParent接口或构造时传入父类对象则会将当前指针加入到指针列表中,而父对象析构前,将会按加入顺序递归析构其子对象。
QObject::QObject(QObject *parent)
: d_ptr(new QObjectPrivate)
{
...
setParent(parent); /* 设置父对象 */
...
}
void QObject::setParent(QObject *parent)
{
Q_D(QObject);
Q_ASSERT(!d->isWidget);
d->setParent_helper(parent);
}
q
指针存入到父类的children列表容器中。#define Q_Q(Class) Class * const q = q_func()
void QObjectPrivate::setParent_helper(QObject *o)
{
...
parent = o;
parent->d_func()->children.append(q); /* 这里的q是QObjectData里面的q_ptr指针 */
...
}
QObject::~QObject()
{
...
if (!d->children.isEmpty())
d->deleteChildren();
...
void QObjectPrivate::deleteChildren()
{
...
for (int i = 0; i < children.count(); ++i) {
currentChildBeingDeleted = children.at(i);
children[i] = 0;
delete currentChildBeingDeleted;
}
children.clear();
...
}