【QT学习十一】QThread
一、引言
在现代软件开发中,多线程编程变得越来越重要,尤其是对于需要处理并发任务的应用程序。Qt C++ 框架提供了强大的多线程支持,使得开发者能够轻松地创建和管理多线程应用。
在 Qt 中,多线程的实现主要基于 QThread 类。QThread 提供了一个线程对象,允许开发者通过继承 QThread 类并实现 run() 函数来定义线程的执行体
二、一个QThread实例
#include <QCoreApplication>
#include <QThread>
#include <QDebug>class MyThread : public QThread {
public:void run() override {for (int i = 0; i < 5; ++i) {qDebug() << "Thread is running" << i;sleep(1);}}
};int main(int argc, char *argv[]) {QCoreApplication a(argc, argv);// 创建线程对象MyThread thread;// 启动线程thread.start();// 主线程继续执行其他任务for (int i = 0; i < 3; ++i) {qDebug() << "Main thread is running" << i;QThread::sleep(1);}// 等待线程结束thread.wait();return a.exec();
}
在这个示例中,MyThread 类继承自 QThread,并重写了 run() 函数。在 main() 函数中,我们创建了 MyThread 的实例 thread,并通过 start() 启动了一个新线程。同时,主线程继续执行其他任务。
三、QThread 类的一些关键特性和用法
1、创建线程
通过继承 QThread 类,可以创建一个自定义的线程类。在自定义的类中,可以重写 run() 函数,该函数定义了线程的执行体。
class MyThread : public QThread {
public:void run() override {// 线程的执行体}
};
2、启动线程
使用 start() 函数来启动线程。一旦调用了 start(),run() 函数将在新线程中执行。
MyThread thread;
thread.start();
3、等待线程结束
使用 wait() 函数来等待线程执行结束。这确保主线程等待子线程完成后再继续执行。
thread.wait();
4、线程间通信
Qt 提供了信号和槽机制,可以用于在线程之间进行安全的通信。在多线程中,使用信号和槽是一种避免共享资源问题的方式。
connect(sender, SIGNAL(sendMessage(QString)), receiver, SLOT(receiveMessage(QString)));
5、线程安全
QThread 提供了一些方法来确保线程的安全性,如 mutex 和 atomic 操作,以避免多线程竞争条件。
QMutex mutex;
mutex.lock();
// 线程安全的操作
mutex.unlock();
四、Qthread注意事项
在使用 QThread 进行多线程编程时,有一些注意事项需要考虑,以确保正确、安全、高效地使用线程。以下是一些关键的注意事项:
1、不要直接调用 run 函数
QThread 中的 run() 函数是线程执行体,但不应该直接调用它。正确的方式是通过 start() 函数启动线程,run() 函数会在新线程中自动执行。
// 错误的方式
MyThread thread;
thread.run(); // 不要这样调用// 正确的方式
MyThread thread;
thread.start(); // 通过 start 函数启动线程
2、避免直接继承 QThread
直接继承 QThread 并重写 run() 函数是一种方式,但并不总是最好的。推荐使用组合的方式,将线程逻辑放在另外的类中,然后在 QThread 的子类中创建该类的实例。
class Worker : public QObject {Q_OBJECT
public slots:void doWork() {// 线程的执行体}
};class MyThread : public QThread {
public:void run() override {Worker worker;connect(this, &MyThread::startWork, &worker, &Worker::doWork);emit startWork();}signals:void startWork();
};
3、线程安全
考虑多线程访问共享资源时的线程安全性。使用互斥锁 (QMutex) 或其他同步机制来确保对共享数据的访问是线程安全的。
QMutex mutex;
mutex.lock();
// 访问共享资源
mutex.unlock();
4、注意内存管理
在多线程环境中,注意内存管理问题。确保在合适的时候释放线程中创建的资源,以避免内存泄漏。
5、合理设置线程属性
使用 setObjectName() 为线程设置名称,以方便调试。可以使用 setPriority() 设置线程的优先级,但要注意过度使用优先级可能导致不稳定的行为。
MyThread thread;
thread.setObjectName("WorkerThread");
thread.setPriority(QThread::LowPriority);
6、不要在主线程中直接操作子线程的对象
子线程的对象应该通过信号和槽来进行通信。在主线程中直接操作子线程的对象可能导致线程安全问题。
// 错误的方式
MyThread thread;
Worker worker;
worker.doWork(); // 避免在主线程中直接调用子线程对象的函数// 正确的方式
MyThread thread;
Worker worker;
connect(&thread, &MyThread::startWork, &worker, &Worker::doWork);
thread.start();
五、总结
QThread 是 Qt 中处理多线程编程的基础,并提供了一些辅助工具和机制,以简化开发者在并发环境中的工作。但在某些情况下,使用 QtConcurrent 或 Qt Concurrent 命名空间中的高级功能可能更为方便。这些功能提供了更高层次的抽象,用于并发和并行处理。
Qt C++ 提供了强大而灵活的多线程支持,使得多线程编程变得更加容易。通过 QThread 类的使用,开发者能够轻松创建和管理多线程应用。同时,信号和槽机制为线程间的通信提供了一种安全而高效的方式。
相关文章:
【QT学习十一】QThread
一、引言 在现代软件开发中,多线程编程变得越来越重要,尤其是对于需要处理并发任务的应用程序。Qt C 框架提供了强大的多线程支持,使得开发者能够轻松地创建和管理多线程应用。 在 Qt 中,多线程的实现主要基于 QThread 类。QThrea…...
Mybatis 39_使用MBG生成代码
此2个插件均未晚装成功!!!! 安装 MyBatipse插件 MyBatipse插件 - 开发MyBatis应用的Eclipse插件- 自动完成- 有效性验证- Mapper视图使用MBG MyBatis Generator (MBG):根据底层数据表来自动生成Mapper组件只要两步即可: (1) 提供一个简单的配置文件,告诉MBG连接数据…...
Hudi metadata table(元数据表)
什么是metadata表 Metadata表即Hudi元数据表,是一种特殊的Hudi表,对用户隐藏。该表用于存放普通Hudi表的元数据信息。Metadata表包含在普通Hudi表内部,与Hudi表是一一对应关系。 元数据表的作用 ApacheHudi元数据表可以显著提高查询的读/写性能。元数据表的主要目的是消…...
提高iOS App开发效率的方法
引言 随着智能手机的普及,iOS App开发成为越来越受欢迎的技术领域之一。许多人选择开发iOS应用程序来满足市场需求,但是iOS App开发需要掌握一些关键技术和工具,以提高开发效率和质量。本文将介绍一些关键点,可以帮助你进行高效的…...
MPU机制与实现详解
目录 MPU机制与实现详解 Partition元素-MPU Partition实现元素OSApplication Partition元素-RTE MPU机制与实现详解 1、freedom from interference 此概念来自ISO26262-1:多个元素之间没有可能导致违反安全目标的级联故障,称之为免于干涉。 在左侧的…...
pom文件冲突引起的Excel无法下载
问题一:之前生产环境上可以进行下载Excel的功能突然不能用了 报错提示信息: NoClassDefFoundError: Could not initialize class org.apache.poi.xssf.usermodel.XSSFWorkbook, 在最开始初始化的时候找不到对应的类,虽然我的Libr…...
【HarmonyOS4.0】第十篇-ArkUI布局容器组件(二)
三、层叠布局容器(Stack) 堆叠容器组件 Stack的布局方式是把子组件按照设置的对齐方式顺序依次堆叠,后一个子组件覆盖在前一个子组件上边。 注意:Stack 组件层叠式布局,尺寸较小的布局会有被遮挡的风险, …...
PLECS如何下载第三方库并导入MOSFET 的xml文件,xml库路径添加方法及相关问题
1. 首先xml库的下载,PLECS提供了一个跳转的链接。 https://www.plexim.com/download/thermal_models 2. 下载一个库(以最后一个Wolfspeed为例,属于CREE的SiC MOSFET) 下载这个就行,都包含了。不信自己可以试试再下载…...
使用emu8086实现——子程序的设计
一、实验目的 学习子程序的结构、特点,以及子程序的设计和调试方法 二、实验内容 1、从字符串中删除一个字符,并存储到寄存器AX中。 代码及注释: data segmentstring db exas ;字符串内容leng dw $-string ; 字符串长度key db x …...
快速排序、归并排序、希尔排序(2023-12-25)
参考文章 十大经典排序算法总结整理_十大排序算法-CSDN博客 推荐文章 算法:归并排序和快排的区别_归并排序和快速排序的区别-CSDN博客 package com.tarena.test.B20; import java.util.Arrays; import java.util.StringJoiner; public class B25 { static i…...
Qt SDL2播放Wav音频
这里介绍两种方法来实现Qt播放Wav音频数据。 方法一:使用QAudioOutput pro文件中加入multimedia模块。 #include <QApplication> #include <QFile> #include <QAudioFormat> #include <QAudioOutput>int main(int argc, char *argv[]) {…...
[ACM学习] 动态规划基础之一二三维dp
课内学习的动态规划 有记忆的迭代 优化解的结构:原始问题的一部分解是子问题的解 三要素:1.子问题 2.状态的定义 3.状态转移方程 定义 线性dp的一道例题 dp[i]表示以位置 i 结尾的方案总数,dp[4]2,因为:首先只放一…...
Qt点击按钮在其附近弹出一个窗口
效果 FS_PopupWidget.h #ifndef FS_POPUPWIDGET_H #define FS_POPUPWIDGET_H#pragma once#include <QToolButton> #include <QWidgetAction> #include <QPointer>class QMenu;class FS_PopupWidget : public QToolButton {Q_OBJECTpublic:FS_PopupWidget(QW…...
Springboot注解@Configuration和@Bean注解作用,生命周期
简介: Configuration 类是定义 bean 配置的地方,而 Bean 方法是具体创建 bean 实例的方法。 Configuration 作用: Configuration 注解用于定义配置类,表明该类包含一个或多个 bean 定义的方法。Spring 容器在启动时会自动扫描这些…...
30天精通Nodejs--第十五天:Websocket
引言 这里我们将继续深入探讨另一项强大且实时性极高的网络通信技术——WebSocket。通过本篇文章,将全面了解如何在Node.js环境中利用WebSocket实现服务端与客户端之间双向、低延迟的数据传输,并掌握其基础用法以及一些高级应用场景。 基础用法 安装WebSocket库 在Node.j…...
C++深入学习之STL:2、适配器、迭代器与算法部分
适配器概述 C标准模板库(STL)中提供了几种适配器,这些适配器主要用于修改或扩展容器类的功能。STL中的适配器主要包括以下几种: 1、迭代器适配器:迭代器适配器提供了一种机制,可以将非迭代器对象转换为迭代器对象。比如back_ins…...
Tiktok/抖音旋转验证码识别
一、引言 在数字世界的飞速发展中,安全防护成为了一个不容忽视的课题。Tiktok/抖音,作为全球最大的短视频平台之一,每天都有数以亿计的用户活跃在其平台上。为了保护用户的账号安全,Tiktok/抖音引入了一种名为“旋转验证码”的安…...
【Java 设计模式】设计原则
文章目录 ✨单一职责原则(SRP)✨开放/封闭原则(OCP)✨里氏替换原则(LSP)✨依赖倒置原则(DIP)✨接口隔离原则(ISP)✨合成/聚合复用原则(CARP&#…...
Druid连接池工具公式化SQL附踩坑记录
1. 需求 使用Druid连接池工具格式化sql用于回显时候美观展示 2. 代码示例 2.1 依赖 <dependency><groupId>com.alibaba</groupId><artifactId>druid</artifactId><version>1.2.6</version> </dependency> 2.2 ParseUtils…...
Linux内核--网络协议栈(二)UDP数据包发送
目录 一、引言 二、数据包发送 ------>2.1、数据发送流程 三、协议层注册 ------>3.1、socket系统调用 ------>3.2、socket创建 ------>3.3、协议族初始化 ------>3.4、对应协议的socket创建 ------>3.5、协议注册 四、通过套接字发送网络数据 --…...
VB.net复制Ntag213卡写入UID
本示例使用的发卡器:https://item.taobao.com/item.htm?ftt&id615391857885 一、读取旧Ntag卡的UID和数据 Private Sub Button15_Click(sender As Object, e As EventArgs) Handles Button15.Click轻松读卡技术支持:网站:Dim i, j As IntegerDim cardidhex, …...
STM32标准库-DMA直接存储器存取
文章目录 一、DMA1.1简介1.2存储器映像1.3DMA框图1.4DMA基本结构1.5DMA请求1.6数据宽度与对齐1.7数据转运DMA1.8ADC扫描模式DMA 二、数据转运DMA2.1接线图2.2代码2.3相关API 一、DMA 1.1简介 DMA(Direct Memory Access)直接存储器存取 DMA可以提供外设…...
python爬虫:Newspaper3k 的详细使用(好用的新闻网站文章抓取和解析的Python库)
更多内容请见: 爬虫和逆向教程-专栏介绍和目录 文章目录 一、Newspaper3k 概述1.1 Newspaper3k 介绍1.2 主要功能1.3 典型应用场景1.4 安装二、基本用法2.2 提取单篇文章的内容2.2 处理多篇文档三、高级选项3.1 自定义配置3.2 分析文章情感四、实战案例4.1 构建新闻摘要聚合器…...
SpringBoot+uniapp 的 Champion 俱乐部微信小程序设计与实现,论文初版实现
摘要 本论文旨在设计并实现基于 SpringBoot 和 uniapp 的 Champion 俱乐部微信小程序,以满足俱乐部线上活动推广、会员管理、社交互动等需求。通过 SpringBoot 搭建后端服务,提供稳定高效的数据处理与业务逻辑支持;利用 uniapp 实现跨平台前…...
论文解读:交大港大上海AI Lab开源论文 | 宇树机器人多姿态起立控制强化学习框架(一)
宇树机器人多姿态起立控制强化学习框架论文解析 论文解读:交大&港大&上海AI Lab开源论文 | 宇树机器人多姿态起立控制强化学习框架(一) 论文解读:交大&港大&上海AI Lab开源论文 | 宇树机器人多姿态起立控制强化…...
【碎碎念】宝可梦 Mesh GO : 基于MESH网络的口袋妖怪 宝可梦GO游戏自组网系统
目录 游戏说明《宝可梦 Mesh GO》 —— 局域宝可梦探索Pokmon GO 类游戏核心理念应用场景Mesh 特性 宝可梦玩法融合设计游戏构想要素1. 地图探索(基于物理空间 广播范围)2. 野生宝可梦生成与广播3. 对战系统4. 道具与通信5. 延伸玩法 安全性设计 技术选…...
GC1808高性能24位立体声音频ADC芯片解析
1. 芯片概述 GC1808是一款24位立体声音频模数转换器(ADC),支持8kHz~96kHz采样率,集成Δ-Σ调制器、数字抗混叠滤波器和高通滤波器,适用于高保真音频采集场景。 2. 核心特性 高精度:24位分辨率,…...
Linux C语言网络编程详细入门教程:如何一步步实现TCP服务端与客户端通信
文章目录 Linux C语言网络编程详细入门教程:如何一步步实现TCP服务端与客户端通信前言一、网络通信基础概念二、服务端与客户端的完整流程图解三、每一步的详细讲解和代码示例1. 创建Socket(服务端和客户端都要)2. 绑定本地地址和端口&#x…...
scikit-learn机器学习
# 同时添加如下代码, 这样每次环境(kernel)启动的时候只要运行下方代码即可: # Also add the following code, # so that every time the environment (kernel) starts, # just run the following code: import sys sys.path.append(/home/aistudio/external-libraries)机…...
Unity UGUI Button事件流程
场景结构 测试代码 public class TestBtn : MonoBehaviour {void Start(){var btn GetComponent<Button>();btn.onClick.AddListener(OnClick);}private void OnClick(){Debug.Log("666");}}当添加事件时 // 实例化一个ButtonClickedEvent的事件 [Formerl…...
