QT 不阻塞线程,达到延时的作用

这篇具有很好参考价值的文章主要介绍了QT 不阻塞线程,达到延时的作用。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

有时候需要处理一些跟界面无关的但非常耗时的事情,这些事情跟界面在同一个线程中,由于时间太长,导致界面无法响应,处于“假死”状态。例如:在应用程序中保存文件到硬盘上,从开始保存直到文件保存完毕,程序不响应用户的任何操作,窗口也不会重新绘制,从而处于“无法响应”状态,这是一个非常糟糕的体验 。
     在这种情况下,有一种方法是使用多线程,即在子线程中处理文件保存,主线程负责界面相关。
     而如果不想使用多线程,最简单的办法就是在文件保存过程中频繁调用QApplication::processEvents()。该函数的作用是让程序处理那些还没有处理的事件,然后再把使用权返回给调用者。

Qt一般使用QThread::sleep()来延时,但是这样会阻塞住线程

此时,可以用

QTime delayTime = QTime::currentTime().addMSecs(3000);    //在当前时间上增加3S
/* lyh delete -> 避免有拉拽小票冲突 */
while( QTime::currentTime() < delayTime)
    QCoreApplication::processEvents(QEventLoop::AllEvents, 100);
还有另外一种方法,更加简洁,但是本质是一样的,利用QEventLoop

QEventLoop loop;
QTimer::singleShot(100, &loop, SLOT(quit()));
loop.exec();

场景——run函数:
写多线程的时候,可以从QThread派生一个线程类,而且要重写run函数。重写run函数的时候,底部要加一个exec()事件循环。

void MyThread::run()
{
    //希望在线程中完成的操作...
 
    exec();//事件循环
}
跟main函数一样,这里必须写事件循环,否则run函数执行完前面代码之后会直接结束,线程就结束了。

这里穿插一个概念,所谓线程,不是new了一个线程对象就是线程,这个线程对象其实是在父线程中,跟其它对象一样,new了一个实例而已。它仅仅存在于父线程,它可以作为控制线程的句柄。而真正的线程过程,是run函数启动以后,写在run函数中的代码。所以使用继承QThread并重写run函数的方式实现线程时,一定切记,不是所有函数就一定会在线程中执行,除非它被run函数调用,或者在run当中使用rambda写匿名槽函数。而写匿名槽函数的时候,接收者千万别写this,this指针是指向父线程的线程对象,能作为句柄控制线程,但this隶属于父线程。所以一旦写了this是接收者,这个匿名槽函数会在父线程执行。而子线程中创建对象时,也不要指定parent为this。

所以,在run函数中写exec,它会阻止run函数结束,让子线程始终等待消息队列的任务,从而实现利用信号槽进行线程通信。

场景——子线程对象
上面说过线程的实现,离不开父线程的线程对象,它仅仅是子线程的操作句柄。如果一定要让一个槽函数运行于子线程中,可能还少不了要写个对象再使用movetothread让它进入线程。所以,个人认为,写线程的时候,更好的方法是不要继承QThread并重写run函数。而是把要执行的逻辑写成一个类,实例化以后movetothread,可以确保它一定是在子线程中运行。

MyObject *obj = new MyObject;
QThread *thd = new QThread;
obj->setParent(NULL);
obj->moveToThread(thd);
thd->start();文章来源地址https://www.toymoban.com/news/detail-477968.html

到了这里,关于QT 不阻塞线程,达到延时的作用的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 为什么有时候ADSL访问速度会很慢

      为什么有时候ADSL访问速度会很慢        1.网卡绑定的协议太多。上网速度慢,在局域网用户中很常见,原因是网卡绑定的协议太多。网卡上如果绑定了许多协议,当数据通过网卡时,计算机就要花费很多时间来确定这个数据使用哪种协议来传送,这时用户就会感觉上网慢

    2024年02月08日
    浏览(36)
  • M330左键有时候按下没反应的解决 - 换微动

    罗技M330鼠标左键有时候按下没反应,原因是微动老了要换新的了。 1、电烙铁/锡条(最主要的是这两个,其他可以不需要,操作电烙铁时候一定要小心,不要碰到被烫到) 2、小号螺丝刀,给眼镜用的那种,用来拆鼠标的螺丝(共2个螺丝) 视频教程: https://www.bilibili.com/vi

    2024年02月09日
    浏览(41)
  • 在Android Studio导入一个项目之后,通常需要下载Gradle的相应版本,但是AS的自动下载很慢,有时候甚至会失败。会出现类似Error:connect time out等错误...

    用Android Studio导入一个项目时,用Gradle构建过程中报错误,估计是下载gradle.zip文件时访问不到,应该是被墙了,网速太慢,下载不了外网资源。错误有如下情况:1、加载过慢2、下载超时3、下载失败 解决方法如下: 1、下载对应的gradle版本 在Project的视图下,找到gradle,里面的

    2024年02月03日
    浏览(62)
  • Qt QQueue 安全的多线程队列、阻塞队列

    在C++中,queue是一个模板类,用于实现队列数据结构,遵循先进先出的原则。 ♦ 常用方法: · ♦ 简单使用: · ♦ 打印: · QQueue 继承与 QList ♦ 常用方法: · ♦ 实例: · ♦ 打印: · 在多线程编程中,由于QQueue并不是线程安全的,因此我们需要先使用互斥锁(QMutex)来保

    2024年02月16日
    浏览(25)
  • 空闲任务与阻塞延时(笔记)

    软件延时是让CPU等待达到延时效果。 而RTOS的优势是可以充分发挥CPU的性能,永远不会让CPU闲着。 RTOS中的延时叫做阻塞延时 当没有其他任务可以运行时,RTOS会为CPU创建一个空闲任务,然后CPU去执行。 在RTOS中,空闲任务是系统在调度器创建的优先级最低的任务,空闲任务主

    2024年02月03日
    浏览(62)
  • verilog的非阻塞赋值、延拍和电路延时

    1.时序电路使用非阻塞赋值,always块中的语句顺序无影响; 2.非阻塞赋值中d和out的新值在本次上升沿计算之后,下一次上升沿才会生效; 阻塞赋值会使信号变化立即生效 3.实际电路中,下一次上升沿值生效时会有一定触发器延时(上一拍采数时,往左边偏一点采值)。

    2024年03月24日
    浏览(28)
  • 【HAL库】STM32CubeMX开发----非阻塞延时实验----SysTick(滴答定时器)中断

    STM32CubeMX 下载和安装 详细教程 【HAL库】STM32CubeMX开发----STM32F103/F207/F407----目录 HAL库 有自带的 ms级 延时函数: HAL_Delay(); 缺点: 这是 阻塞延时 方式,就是延时期间,什么都不能干,这样很浪费资源。 这篇文章主要介绍,利用 SysTick(滴答定时器)中断 实现 非阻塞延时 的实验

    2024年02月16日
    浏览(40)
  • 线程池的一个BUG导致CPU达到100%

    给大家分享一个关于 ScheduledExecutorService 线程池的 BUG 啊,这个 BUG 能直接把 CPU 给飚到 100%,希望大家永远踩不到。 但是,有一说一,一般来说也很难踩到。 到底咋回事呢,让我给你细细说说。 Demo

    2024年02月16日
    浏览(26)
  • 10.阻塞队列和线程池

    阻塞队列(BlockQueue) 非阻塞方法 add 往满的队列中添加元素会报错 remove 从空的队列中移除元素会报错 offer 往满的队列中添加元素会返回false poll 从空的队列中移除元素会返回null 阻塞方法 put take 使用场景: 阻塞队列通常使用在生产者消费者设计模式当中,生产者不用关心生成的

    2024年02月04日
    浏览(26)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包