C++ 为什么我必须为QLabel动态分配内存才能使其工作?
此代码不会动态分配内存,不会在窗口上显示任何标签C++ 为什么我必须为QLabel动态分配内存才能使其工作?,c++,qt,dynamic-memory-allocation,qlabel,C++,Qt,Dynamic Memory Allocation,Qlabel,此代码不会动态分配内存,不会在窗口上显示任何标签 MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent) { QLabel l; l.setText ("cdsadsaf"); l.setParent (this); } 动态分配内存后,将显示标签 MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent) { Q
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel l;
l.setText ("cdsadsaf");
l.setParent (this);
}
动态分配内存后,将显示标签
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(this);
label->setText("first line\nsecond line");
}
为什么QLabel需要动态内存分配才能工作?在堆栈上创建
QLabel
时,当函数返回时,它会被删除。当父窗口小部件更新其显示时,QLabel
不再存在
在堆上创建它允许它在调用函数之后继续存在。在堆栈上创建
QLabel
时,函数返回时它会被删除。当父窗口小部件更新其显示时,QLabel
不再存在
在堆上创建它允许它在调用函数之后继续存在。这不是必需的。这里有典型的范围问题 第一种情况是在堆栈上创建
QLabel
,当您退出构造函数时,它“死亡”
在第二个窗口中,它继续存在1)因为它是动态分配的,2)您实际上为它分配了一个父窗口-这是您的主窗口。如果不执行2),效果将与第一种情况相同,但更糟的是,您将创建内存泄漏:
内存泄漏
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(); # no parent
label->setText("first line\nsecond line");
}
没有由于父项被分配给标签而导致的内存泄漏
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(this); # main window is the parent and will take care of destroying the label when its own destructor is called
label->setText("first line\nsecond line");
}
您可以避免在堆上分配QLabel
,但仍然可以通过将其移动到更广的范围来使用它。由于标签将显示在主窗口中,因此可以创建类成员标签。不需要动态分配,因为只要窗口实例处于活动状态,它就会保持活动状态
class MainWindow : public QMainWindow
{
...
private:
QLabel l;
}
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
this->l.setText ("cdsadsaf");
}
如评论中所述(再次感谢!)
setParent(…)
在这里不是必需的,除非您希望为内存管理以外的内容建立父子关系。请参阅下面的注释。这不是必需的。这里有典型的范围问题
第一种情况是在堆栈上创建QLabel
,当您退出构造函数时,它“死亡”
在第二个窗口中,它继续存在1)因为它是动态分配的,2)您实际上为它分配了一个父窗口-这是您的主窗口。如果不执行2),效果将与第一种情况相同,但更糟的是,您将创建内存泄漏:
内存泄漏
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(); # no parent
label->setText("first line\nsecond line");
}
没有由于父项被分配给标签而导致的内存泄漏
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(this); # main window is the parent and will take care of destroying the label when its own destructor is called
label->setText("first line\nsecond line");
}
您可以避免在堆上分配QLabel
,但仍然可以通过将其移动到更广的范围来使用它。由于标签将显示在主窗口中,因此可以创建类成员标签。不需要动态分配,因为只要窗口实例处于活动状态,它就会保持活动状态
class MainWindow : public QMainWindow
{
...
private:
QLabel l;
}
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
this->l.setText ("cdsadsaf");
}
如评论中所述(再次感谢!)setParent(…)
在这里不是必需的,除非您希望为内存管理以外的内容建立父子关系。见下面的评论
此代码不会动态分配内存,不会在窗口上显示任何标签
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel l;
l.setText ("cdsadsaf");
l.setParent (this);
}
这是因为一旦您从构造函数返回,标签就会超出范围。标签的生命周期如下所示。标签本身就是一个QLabel
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel label; // label is born
label.setText ("cdsadsaf"); // label is alive
label.setParent (this); // label is alive
} // label dies
动态分配内存后,将显示标签
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(this);
label->setText("first line\nsecond line");
}
这是因为标签没有超出范围。指向它的指针可以,但这并不重要。请注意,label
只是一个指针,而QLabel
对象独立于指向它的指针而存在
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(this); // label is born, QLabel is born
label->setText("first line\nsecond line"); // label is alive, QLabel is alive
} // label dies, QLabel is alive
为什么QLabel工作需要动态内存分配
不是。由于使用了动态分配,您碰巧给了QLabel一个生存的机会,但这只是巧合
您可以将标签作为父对象本身的一部分,这样就不需要单独分配。编译器将为您管理内存
#include <QtWidgets>
class MainWindow : public QMainWindow {
QWidget m_central;
QGridLayout m_layout{&m_central};
QLabel m_label{"Hello, World"};
public:
MainWindow(QWidget * parent = {}) : QMainWindow{parent} {
m_layout.addWidget(&m_label, 0, 0);
setCentralWidget(&m_central);
}
};
int main(int argc, char ** argv) {
QApplication app{argc, argv};
MainWindow w;
w.show();
return app.exec();
}
#包括
类主窗口:公共QMainWindow{
九龙文娱艺术中心;;
QGridLayout m_layout{&m_central};
QLabel m_标签{“你好,世界”};
公众:
主窗口(QWidget*parent={}):QMainWindow{parent}{
m_layout.addWidget(&m_标签,0,0);
setCentralWidget(&m_central);
}
};
int main(int argc,字符**argv){
QApplication app{argc,argv};
主窗口w;
w、 show();
返回app.exec();
}
此代码不会动态分配内存,不会在窗口上显示任何标签
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel l;
l.setText ("cdsadsaf");
l.setParent (this);
}
这是因为一旦您从构造函数返回,标签就会超出范围。标签的生命周期如下所示。标签本身就是一个QLabel
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel label; // label is born
label.setText ("cdsadsaf"); // label is alive
label.setParent (this); // label is alive
} // label dies
动态分配内存后,将显示标签
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(this);
label->setText("first line\nsecond line");
}
这是因为标签没有超出范围。指向它的指针可以,但这并不重要。请注意,label
只是一个指针,而QLabel
对象独立于指向它的指针而存在
MainWindow::MainWindow(QWidget *parent)
: QMainWindow(parent)
{
QLabel *label = new QLabel(this); // label is born, QLabel is born
label->setText("first line\nsecond line"); // label is alive, QLabel is alive
} // label dies, QLabel is alive
为什么QLabel工作需要动态内存分配
不是。由于使用了动态分配,您碰巧给了QLabel一个生存的机会,但这只是巧合
您可以将标签作为父对象本身的一部分,这样就不需要单独分配。编译器将为您管理内存
#include <QtWidgets>
class MainWindow : public QMainWindow {
QWidget m_central;
QGridLayout m_layout{&m_central};
QLabel m_label{"Hello, World"};
public:
MainWindow(QWidget * parent = {}) : QMainWindow{parent} {
m_layout.addWidget(&m_label, 0, 0);
setCentralWidget(&m_central);
}
};
int main(int argc, char ** argv) {
QApplication app{argc, argv};
MainWindow w;
w.show();
return app.exec();
}
#包括
类主窗口:公共QMainWindow{
九龙文娱艺术中心;;
QGridLayout m_layout{&m_central};
QLabel m_标签{“你好,世界”};
公众:
主窗口(QWidget*parent={}):QMainWindow{parent}{
m_layout.addWidget(&m_标签,0,0);
setCentralWidget(&m_central);
}
};
int main(int argc,字符**argv){
QApplication app{argc,argv};
主窗口w;
w、 show();
返回app.exec();
}
如果您在类成员的小部件上调用setParent
,它不会被删除吗