项目开发过程中,碰到一个问题,关闭窗口后,程序会崩溃掉。找了好久才发现是设置了这个属性setAttribute(Qt::WA_DeleteOnClose)
未设置该属性时,你去关闭窗口,窗口资源不会立即释放,窗口只是隐藏了。当调用析构函数时,窗口资源才会真正释放。
而设置了该属性,那么你去关闭窗口,窗口资源会立即释放掉。
可以看下代码:
widget.cpp
#include "widget.h"
#include "ui_widget.h"
Widget::Widget(QWidget *parent) :
QWidget(parent),
ui(new Ui::Widget)
{
ui->setupUi(this);
this->setAttribute(Qt::WA_DeleteOnClose);
}
Widget::~Widget()
{
delete ui;
}
main.cpp
#include "widget.h"
#include <QApplication>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
Widget w;
w.show();
return a.exec();
}
设置该属性后,我们关闭窗口,窗口资源会立即释放。而程序结束时,又会调用析构函数,析构函数中对窗口资源又释放了一次。程序就会崩溃掉。
解决方法有两种
第一种,那么我们就不要设置该属性了。
第二种,动态申请对象,然后不要去手动调用delete释放资源,析构函数不会被调用,就不会造成窗口资源重复释放的问题。main.cpp修改如下
#include "widget.h"
#include <QApplication>
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
Widget *w = new Widget;
w->show();
return a.exec();
}
建议:平时使用时最好不要设置这个属性 setAttribute(Qt::WA_DeleteOnClose)。我在网上看到很多情况下设置这个属性是由于关闭窗口后,进程未退出,所以很多文章建议设置该属性。但是关闭窗口后程序未退出的原因并不是因为这个,一般是因为程序中有阻塞的线程阻止了窗口的销毁,因此关闭窗口后进程未退出,出现这种情况就需要排查下程序中有哪些阻塞线程导致了窗口的销毁,从而导致进程未退出。