繁体   English   中英

Qt 僵尸:使用 QTimer 调用包含 new 的函数

[英]Qt zombies: Calling functions containing new with QTimer

我正在尝试使用刷新率为 1s 的QTimer显示一个动态更新的表。 我正在调用 function create_table ,它又调用create_title 代码运行没有任何抱怨,但跟踪 memory 的使用情况,发现它一直在稳步上升,直到程序变得无响应或崩溃。

void MainWindow::TableDisplay(QWidget *tab) {
    auto timer = new QTimer(this);
    connect(timer, &QTimer::timeout, [refreshed_table_data, tab, this]() {
            auto tableView = create_table(tab, refreshed_table_data, "My table");
    });
    timer->start(1000);
}

罪魁祸首似乎是各种new语句(由我的代码中的注释指示),每次QTimer运行循环时,它们似乎都会产生新的僵尸/泄漏。

auto create_title(const std::string &title, QWidget * widget) {
    auto tableTitle = new QLabel(title.c_str(), widget); // <-- new
    tableTitle->setAlignment(Qt::AlignLeft);
    tableTitle->show();
}
auto create_table(QWidget * tab,
                  const std::vector<std::string> &v,
                  const std::string &title) {
    auto tableView = new QTableView(tab); // <-- new
    auto model = new MyModel(v, tab); // <-- new
    tableView->setModel(model);
    tableView->setStyle(new QProxyStyle(QStyleFactory::create("Fusion"))); // <-- new
    tableView->setHorizontalHeader(new QHeaderView(Qt::Horizontal)); // <-- new
    create_title(title, tab);
    tableView->show();
    return tableView;
}

一种解决方案可能是将指针由new初始化为MainWindow的成员变量,以便它们只定义一次。 但是,如果我要调用几个这样的定时函数,它很快就会变得很麻烦,更何况考虑到有渲染元素,比如new QProxyStyle(QStyleFactory::create("Fusion"))等需要的行被赋予成员变量的地位。

我尝试用QScopePointer包装new语句,但不幸的是,在create_table退出其 scope 后,实例立即被破坏,导致表格图形无法呈现。

在不创建僵尸的情况下编写create_table的正确方法是什么?

对于问题本身:您的createTable方法可以调用QTimer::singleShot在一秒钟后安排更新。

auto create_table(QWidget * tab,
                  const std::vector<std::string> &v,
                  const std::string &title) {
    ...
    QTimer::singleShot(1000 /*ms*/, this /*context*/, [this, tab, v, title]() {
            create_table(tab, v, title);
    });
    return tableView;
}

然而,正如 Igor 所指出的,整个方法似乎倒退了。 model 应该自我更新,最好是基于事件的,但如果它必须轮询外部资源,它可能必须自己使用计时器。

为视图设置一个全新的 model 非常昂贵(因为视图必须从头开始创建所有内容)并且可能在 GUI 端产生烦人的副作用。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM