QT多线程问题:子线程中的变量如何传递给主线程?

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了QT多线程问题:子线程中的变量如何传递给主线程?相关的知识,希望对你有一定的参考价值。

本人初学QT,菜鸟一只。
在QT多线程编程中,如何将子线程中的某个变量中的值传递给主线程?比如,我要一个子线程不停读取一个串口,主线程在需要的时候提取子线程中读到的数据,应该如何实现?

参考技术A public int _CurrentThread;

//form1_load中的,启动线程的代码在这里。
private void Form1_Load(object sender, EventArgs e)

//设置最大线程数
int MaxThread = 5;

//获取需要完成的任务列表
OleDbConnection AccessConn = AccessModule.Conn("D:\\Flying Co\\flying.mdb");
string sql = "select * from ty_task where bay_flag=" + false + " order by bay_id asc";

OleDbCommand comm = new OleDbCommand(sql, AccessConn);
OleDbDataReader list = comm.ExecuteReader();

while (list.Read())

ContentParse Spider = new ContentParse();

//如果当前活动线程超过最大线程数,线程休眠
if (Spider.CurrentThread> MaxThread)

Thread.Sleep(2000);

else

//init
Spider.Url = list["bay_task"].ToString();

//启动一个线程
Thread SpiderThread = new Thread(new ThreadStart(Spider.execute));
SpiderThread.Start();
MessageBox.Show(Spider.CurrentThread.ToString());

//任务设置为已处理
sql = "update ty_task set bay_flag=" + true + " where bay_id=" + list["bay_id"].ToString();
AccessModule.Execute(AccessConn, sql);



list.Close();
AccessModule.DisConn(AccessConn);


//线程启动的是这个类的方法
class ContentParse

private string _Url;

//设置任务参数
public string Url

set

_task = value;



public void execute()


//活动线程数加1
Interlocked.Increment(ref _CurrentThread);

//中间处理任务的代码省略

//该线程完成,活动线程减1
Interlocked.Decrement(ref _CurrentThread);


我现在纠结的就是这个Interlocked.Increment(ref _CurrentThread);应该是开一个线程就要加1的对吧?
但是我在form1中间用 MessageBox.Show(Spider.CurrentThread.ToString());,总是0噢

Qt例子,线程间通信,如何在线程外部对线程进行控制,问题请看问题补充,多谢了先

最近在捣腾Qt的多线程,在线程间通信这一块有点疑问,一般而言,使用全局变量或者消息机制来进行线程间通信,这里,得益于Qt的signal/slot机制,我使用使用了信号来通信。

先说一下我对基本概念的理解,从操作系统的角度去看,任一时刻,只能有一个线程在运行,基于这个观点,引出了我的问题。

我有两个线程,线程A和线程B,当A处于运行态的时候,B处于等待态,现在,我在A的运行过程中,想给B传递一些数据,我使用了Qt::DirectConnection来把A的signal连接到B的slot上,而Qt::DirectConnection的说明是直接跳到slot函数去执行slot的代码。现在的问题是,A处于运行态,B处于等待态,并且slot函数属于B线程的,通过Qt::DirectConnection怎么能够跑去执行B线程的代码呢?因为B还在等待,还没轮到B执行,难道是,操作系统先把A挂起,然后唤醒B,接着跑去执行B的slot函数?还是什么机制,因为无论如何,AB是不可能同时处于运行态的,这个Qt::DirectConnection是如何保证B的slot能够马上执行,并且保证代码安全的(而不是一个非法的强制跳转)执行呢?

基于这个问题,我还引出了另外一个问题,如果使用消息机制进行通信,线程A给线程B发送消息只能使用postEvent不能使用sendEvent,postEvent把消息放入B的消息队列中,然后A继续执行,当B运行时,就从消息队列中取出消息进行处理,这样才安全,而sendEvent是马上跑到B的消息处理函数中去处理这个消息,处理完毕后才返回,然后A继续执行,但是这个问题同开始的问题一样,当调用sendEvent时,A处于运行态,B处于等待态,要处理这个消息,必须强制从A跳到B去执行代码,这不是非法的了吗?如果B线程没有唤醒,怎么能够执行B的消息处理函数呢?而B要运行则A必然要挂起,这里就很乱了,难道操作系统会先挂起A,然后唤醒B,B处理完后,又挂起B,再唤醒回A,A从sendEvent返回处开始继续执行。

上面的问题可以简单的概括为,如何在线程外面对线程进行控制,就好比是,在B线程外面(A线程里),对B进行控制,因为一旦处在线程B外面,就表明其他线程(A)在运行态,而本身B线程在挂起,而B没有进入运行态的话,怎么控制得了它的执行序列呢?非常困惑

参考技术A 不要谈什么qt,这个我不懂,但是就谈一谈线程的本质,那都是一样的,2个线程不可能同时进行这个是正确的,但是多核处理器除外。你所说的post和send,我不知道可不可以这么理解,就好象一个是异步,一个是同步。线程A和B肯定都有自己的休息时间,不可能一直执行,要不然那就不叫时间片段了。时间片段和消息,那都是对cpu硬件来说的,具体的转换线程的信号是由cpu处理器完成的。所以说不可能存在B一直休息,然后A去唤醒B的处理函数一说。而应该说B总有休息的时候,也包括运行的时候,那就是根据cpu信号来判断的,他运行的时候,他的消息处理函数总能收到消息,因为消息可以暂时保存在内存中,至于说根据处理函数的决定,然后根据传来时的参数(标名是post还是send)来判断是由当前线程来执行,还是由传来的线程来执行。我是个人理解。你看对不对呢。。本回答被提问者和网友采纳

以上是关于QT多线程问题:子线程中的变量如何传递给主线程?的主要内容,如果未能解决你的问题,请参考以下文章

c语言中,创建的子线程如何给主线程发消息?

qt多线程的问题

Qt例子,线程间通信,如何在线程外部对线程进行控制,问题请看问题补充,多谢了先

QT实现多线程编程

QT多线程及通过事件进行通信(通过自定义事件,然后QApplication::postEvent给主界面,我之前用的是信号槽)

在多线程应用程序中使用 opencv waitKey()