我正在做一个项目,使用 Qt 和一些自定义的 QDialogs 来进行用户输入。由于我的开发箱的硬件限制,我想监控我的应用程序的内存使用情况。我如何执行对话框。
1 void MainWindow::callDialog() {
2 DlgPopConfig dialog(&theApp->cfgPop, m_fnPopCfg, this);
3 dialog.exec();
4 m_fnPopCfg = dialog.fileName();
5 lbl_fnPopCfg->setText(m_fnPopCfg);
6 }
由于对话框是一个局部变量,我希望它在堆栈上创建并在函数结束后立即销毁(第 5 行之后)。当应用反复打开和关闭对话框时,它的 mem 使用率上升,并且永远不会返回到初始值 ['Memory (Working Set)' and 'Memory (Private Working Set)'
columns of Task经理]。我使用了 Application Verifier,启用了所有基本测试,并且没有显示任何错误。内存模式如下所示(数值仅由插图组成):
- 应用程序启动(工作集 = 12000K,私有(private)集 = 6000K)
- 打开 Dialog-1(工作集 = 14000K,私有(private)集 = 7000K)
- 关闭对话框(工作集 = 12010K,私有(private)集 = 6005K)
- 打开 Dialog-2(工作集 = 14020K,私有(private)集 = 7000K)
- 关闭对话框(工作集 = 12010K,私有(private)集 = 6008K)
- 打开 Dialog-3(工作集 = 14080K,私有(private)集 = 7010K)
- 关闭对话框(工作集 = 12040K,私有(private)集 = 6008K)
- ...
那么,有什么想法可以追踪问题的根本原因吗? (其实我在使用静态方法QFileDialog getOpenFileName
, getSaveFileName
的时候也遇到了类似的问题,找了一些讨论here,不过好像没解决)
编辑 我在对话框中使用 QFormLayout,并通过 layout->addRow("label text", mywidget);
添加小部件,我怀疑对象是否被破坏未能干净地去除标签。
编辑 我用 QDialog 创建了一个测试程序,有十个 QLineEdits,使用相同的添加小部件策略。问题仍然存在。 (如果我频繁地创建和关闭对话框,这个测试程序就会出现这个问题,比如每秒 10 次)
主窗口.h
#include <QMainWindow>
#include <QPushButton>
#include <QDialog>
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = 0);
private:
QPushButton * button;
private slots:
void button_click();
};
class Dialog : public QDialog
{
Q_OBJECT
public:
explicit Dialog(QWidget *parent = 0);
};
主窗口.cpp
#include "mainwindow.h"
#include <QApplication>
#include <QFormLayout>
#include <QLineEdit>
#include <QLabel>
MainWindow::MainWindow(QWidget *parent):QMainWindow(parent)
{
button=new QPushButton(this);setCentralWidget(button);
connect(button,SIGNAL(clicked()),SLOT(button_click()));
}
void MainWindow::button_click()
{
Dialog d(this);
d.exec();
}
Dialog::Dialog(QWidget *parent):QDialog(parent)
{
QFormLayout*layout=new QFormLayout(this);
setLayout(layout);
for (int i = 0; i < 10; i++)
{
layout->addRow(QString("%1").arg(i+1), new QLineEdit(this));
}
}
int main(int c,char *argv[])
{
QApplication a(c,argv);
MainWindow w;
w.show();
return a.exec();
}
平台
- Win 7 x64、MinGW 4.7.2 x64 (rubenvb-build)、4GB 内存
- Qt 4.8.5(使用上述工具链本地构建)
- Qt-Creator 2.6.1(使用上述工具链本地构建)
最佳答案
晚了几个月,但这可能会帮助下一个遇到这个问题的人。我正在使用 PySide,但有同样的内存泄漏。结果有两个选项,具体取决于您需要从对话中获取哪些信息:
1) 安排对话框在您完成后删除。
在 Python 中,这看起来像:
dialog = MyDialog(self)
dialog.exec_()
# Do other things with dialog
dialog.deleteLater()
它在您的 C++ 代码中应该看起来很相似:
void MainWindow::button_click()
{
Dialog d(this);
d.exec();
// Do other things with d
d.deleteLater()
}
2) 设置 WA_DeleteOnClose 属性。
我最终将其包含在自定义对话框的构造函数中:
self.setAttribute(PySide.QtCore.Qt.WA_DeleteOnClose)
在您的 C++ 代码中应该看起来像这样:
Dialog::Dialog(QWidget *parent):QDialog(parent)
{
QFormLayout*layout=new QFormLayout(this);
setLayout(layout);
setAttribute(Qt::WA_DeleteOnClose);
for (int i = 0; i < 10; i++)
{
layout->addRow(QString("%1").arg(i+1), new QLineEdit(this));
}
}
这两个都为我修复了内存泄漏,除了如果我连续多次快速打开/关闭对话框偶尔会泄漏 4kb。很抱歉以 Python 为中心的答案——希望这能为人们指明正确的方向。
关于qt - 无法检测 QDialog 内存泄漏的原因,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15674422/