Qt: 详细理解delete与deleteLater (避免访问悬空指针导致程序异常终止)

本文主要是介绍Qt: 详细理解delete与deleteLater (避免访问悬空指针导致程序异常终止),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

前言

珍爱生命,远离悬空指针。

正文

delete

  • 立即删除:调用 delete 后,对象会立即被销毁,其内存会立即被释放。
  • 调用顺序:对象的析构函数会被立即调用,销毁该对象及其子对象。
  • 无事件处理:如果在对象销毁过程中还涉及到信号和槽、事件处理等,直接 delete 可能会导致问题,尤其是在对象正在处理事件时。
  • 适用场景:适用于在确定对象已经不再被使用的情况下,并且不涉及异步处理或事件循环中的删除。
MyWidget *widget = new MyWidget();
delete widget;  // 立即删除对象并释放内存

deleteLater

  • 延迟删除deleteLater 并不会立即销毁对象,而是将销毁任务放入 事件队列,等到当前和其他相关的事件处理完成后才会销毁对象。
  • 异步安全:它适用于对象正在执行某些操作(例如正在响应信号、槽或事件)的情况下,防止对象在事件处理过程中被意外删除而导致崩溃。
  • 事件循环依赖deleteLater 依赖于事件循环(event loop),只有在事件循环的下一个迭代时才会删除对象。如果没有事件循环,该对象可能不会被删除。
  • 适用场景:适用于正在处理事件或信号槽连接的对象,或者需要确保对象在当前操作结束后才安全地删除。
MyWidget *widget = new MyWidget();
widget->deleteLater();  // 延迟删除,等到事件处理完成后才会销毁

不同点总结

  1. 删除时机

    • delete 是同步的,立即删除对象。
    • deleteLater 是异步的,等到事件循环完成后再删除对象。
  2. 使用场景

    • delete 适合在确定对象不会再被使用时直接销毁。
    • deleteLater 适合对象正在处理事件或信号时使用,避免在对象处理完毕之前被删除。
  3. 事件安全性

    • delete 可能会在处理事件时导致崩溃,因为对象会立即被删除。
    • deleteLater 避免了这个问题,确保事件处理完成后再销毁对象。

例子

例如,如果你有一个正在运行的 QWidget,它正在处理某个事件,这时使用 delete 会立即删除该对象,导致未定义行为或崩溃。如果用 deleteLater,对象会等到事件处理完成后再删除。

void MyWidget::someSlot() {// 如果这里直接 delete this,可能导致崩溃// delete this;// 使用 deleteLater 可以安全地删除对象this->deleteLater();
}

相同点总结

二者在销毁对象后,尤其是指针指向的对象,只是释放了指针指向的内存,指针仍然会保留其先前的地址,其指针本身并不会被置为nullptr,此时指针就处于悬空状态,被称为悬空指针,网上和书上说访问悬空指针会造成未定义行为,我遇到最多的情况就是程序异常终止,让你摸不着头脑。所以说在将指针释放掉后,一定一定一定要指向nullptr,这在你编程的时候会避免很多问题。

小结

这篇关于Qt: 详细理解delete与deleteLater (避免访问悬空指针导致程序异常终止)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1147424

相关文章

Python中 try / except / else / finally 异常处理方法详解

《Python中try/except/else/finally异常处理方法详解》:本文主要介绍Python中try/except/else/finally异常处理方法的相关资料,涵... 目录1. 基本结构2. 各部分的作用tryexceptelsefinally3. 执行流程总结4. 常见用法(1)多个e

QT Creator配置Kit的实现示例

《QTCreator配置Kit的实现示例》本文主要介绍了使用Qt5.12.12与VS2022时,因MSVC编译器版本不匹配及WindowsSDK缺失导致配置错误的问题解决,感兴趣的可以了解一下... 目录0、背景:qt5.12.12+vs2022一、症状:二、原因:(可以跳过,直奔后面的解决方法)三、解决方

Debian 13升级后网络转发等功能异常怎么办? 并非错误而是管理机制变更

《Debian13升级后网络转发等功能异常怎么办?并非错误而是管理机制变更》很多朋友反馈,更新到Debian13后网络转发等功能异常,这并非BUG而是Debian13Trixie调整... 日前 Debian 13 Trixie 发布后已经有众多网友升级到新版本,只不过升级后发现某些功能存在异常,例如网络转

Python与MySQL实现数据库实时同步的详细步骤

《Python与MySQL实现数据库实时同步的详细步骤》在日常开发中,数据同步是一项常见的需求,本篇文章将使用Python和MySQL来实现数据库实时同步,我们将围绕数据变更捕获、数据处理和数据写入这... 目录前言摘要概述:数据同步方案1. 基本思路2. mysql Binlog 简介实现步骤与代码示例1

C#文件复制异常:"未能找到文件"的解决方案与预防措施

《C#文件复制异常:未能找到文件的解决方案与预防措施》在C#开发中,文件操作是基础中的基础,但有时最基础的File.Copy()方法也会抛出令人困惑的异常,当targetFilePath设置为D:2... 目录一个看似简单的文件操作问题问题重现与错误分析错误代码示例错误信息根本原因分析全面解决方案1. 确保

基于C#实现PDF转图片的详细教程

《基于C#实现PDF转图片的详细教程》在数字化办公场景中,PDF文件的可视化处理需求日益增长,本文将围绕Spire.PDFfor.NET这一工具,详解如何通过C#将PDF转换为JPG、PNG等主流图片... 目录引言一、组件部署二、快速入门:PDF 转图片的核心 C# 代码三、分辨率设置 - 清晰度的决定因

Java中HashMap的用法详细介绍

《Java中HashMap的用法详细介绍》JavaHashMap是一种高效的数据结构,用于存储键值对,它是基于哈希表实现的,提供快速的插入、删除和查找操作,:本文主要介绍Java中HashMap... 目录一.HashMap1.基本概念2.底层数据结构:3.HashCode和equals方法为什么重写Has

Java利用@SneakyThrows注解提升异常处理效率详解

《Java利用@SneakyThrows注解提升异常处理效率详解》这篇文章将深度剖析@SneakyThrows的原理,用法,适用场景以及隐藏的陷阱,看看它如何让Java异常处理效率飙升50%,感兴趣的... 目录前言一、检查型异常的“诅咒”:为什么Java开发者讨厌它1.1 检查型异常的痛点1.2 为什么说

SysMain服务可以关吗? 解决SysMain服务导致的高CPU使用率问题

《SysMain服务可以关吗?解决SysMain服务导致的高CPU使用率问题》SysMain服务是超级预读取,该服务会记录您打开应用程序的模式,并预先将它们加载到内存中以节省时间,但它可能占用大量... 在使用电脑的过程中,CPU使用率居高不下是许多用户都遇到过的问题,其中名为SysMain的服务往往是罪魁

Java使用正则提取字符串中的内容的详细步骤

《Java使用正则提取字符串中的内容的详细步骤》:本文主要介绍Java中使用正则表达式提取字符串内容的方法,通过Pattern和Matcher类实现,涵盖编译正则、查找匹配、分组捕获、数字与邮箱提... 目录1. 基础流程2. 关键方法说明3. 常见场景示例场景1:提取所有数字场景2:提取邮箱地址4. 高级