问题是这样的:我需要使用一个界面类的方法,不过呢,QT帮助文档里也说了,咱啊,不能在界面类之外操作UI,那关键是怎么滴也需要操作啊,有方法的,那就是通过signals与slot联合操作,线程发出信号,主线程得到信号后来操作界面函数即可。

QT 线程代码

我出了什么问题呢,即程序运行短时间内卡死了,我猜想是递归过深,导致栈溢出崩溃了,我的系统整个资源消耗非常巨大,我检查了我的槽函数。

槽函数

看着像没啥问题的,毕竟我还加上了打印。再瞧瞧connect连接是否出错。

connect连接函数

这也没啥问题啊。

不过我一直在猜想在线程run函数里面的emit发送信号是否是有问题,但无法得到正确的解决方法,毕竟槽是可重入的,按理说,信号不应该是等待上一个信号处理完再发送的吗?难道是,发送者只负责发,不管对象槽怎么个处理法??有疑惑。

这里有篇博客是个合理的理论说法。虽然和信号、槽不一样,但是原理却类似。

Qt学习之系列[9] – QCoreApplication:processEvents()可能会引起递归,导致栈溢出崩溃

博客截图

另外我看到了这篇博客对线程的讲解。

Qt 学习之路 2(74):线程和 QObject

信号与槽连接方式

故而我使用了Qt::BlockingQueuedConnection。

代码

2016年12月21日22:58:31

今天我为了使用OpenGL,移植QT的移植例程到自己的程序里面,OpenGL确实是个大学问的,这里暂且不表,3D图形显示嘛,这里涉及到了一个QTime定时器的东西,因为它要刷新图像,但是我的主线程里面时间可是个娇贵的东西(会妨碍界面的响应,影响交互),我不想让定时器这东西出现在我的主线程里面,所以,我还是需要想想怎么将其挪移到我的子线程里面去,这里需要使用到moveToThread。

将我OpenGLWindow的类运行环境移动到次线程去。

这里可以参考QT的help文档,它主要介绍了两种方式使用QThread。

第一种:

第一种方式

第二种:

第二种方式

第一种方式是让整个类都生存在线程之下,使用movetoThread函数;第二种方式则是只有QThread派生出来的那个子类的run函数是运行在次线程中的,使用while(1)固定整个线程。

  • run函数是线程的起点,调用start后,新线程会默认调用run函数。

可以用实验来证明,我的这个工程中使用的是第二种方式,run函数是阻塞的,使用了while(1),但是在程序将主线程的信号和次线程的槽连接,然后在实际使用中,次线程的槽完全没受影响,照样可以使用,当然,此处我们可以直接打印当前线程的ID,不过网上大多都已经证明了。

另外,第一种方式情况下,照样连接槽和信号,然后在其中一个函数中实现while(1),在尝试着去调用其他槽,发现无法调用。

若我想用第一种方式恐怕还是有点问题,因为我的槽连接方式选择的是Qt::BlockingQueuedConnection,阻塞发送信号的进程,直到接受信号的槽返回,那样的话,我的界面显示不就捉瞎了吗。所以,还是实现一个模态的窗口,强行锁死这个界面看看,但是效果会不太好,可以再想想其他的方法。

2017年5月23日15:52:45

VxWorks上,需要显示的设置线程优先级为low。

线程是有优先级的,就比如在windows和linux上跑该软件,不设置线程优先级则是默认的普通的优先级,但是在VxWorks上则会导致软件卡死,无法运行,这就是系统体系结构不同,线程的实质也不会相同。