Qt 线程中使用socket(勘误)

之前写过两篇关于qt线程中使用socket的文章,昨天有小伙伴看了文章之后和我讨论,然后我发现有一篇文章有问题,今天特地更正一下,误导了之前的小伙伴表示歉意。

 

Qt中将socket放到线程中运行目前我知道比较好的方式还是使用MoveToThread。不过要注意的是只有slot_initSocket()槽中的函数是运行在新的线程中的。就像继承QThread重新实现run()函数一样,只有run()里面的是运行在线程中一样。

程序示例:

    m_socketClient.moveToThread(&m_thread);	

	
    connect(&m_thread, SIGNAL(started()), &m_socketClient, SLOT(slot_initSocket()));	

	
    m_thread.start();

 

经过Qt封装的socket我们使用起来非常方便,有数据到来可以读取后就会触发槽函数,如果使用继承QThread重新实现run()函数的方式,就会不可避免的遇到无法舒服使用信号和槽的情况。而使用MoveToThread则可以规避上面的问题——我们将socket的初始化放到slot_initSocket()函数中,则socket的初始化则是在线程中完成的,那么对应里面信号和槽的连接也是运行在新线程中的。

程序示例:

connect(mp_clsTcpSocket,SIGNAL(readyRead()),this,SLOT(slot_recvServerData()));

 

经过上面的操作,我们的socket就可以运行在线程中了。Qt官方也非常推荐使用moveToThread函数。

示例程序是之前socket拆包、处理粘包程序的修改,大家有兴趣可以了解下。服务器端是接收图片、客户端发送图片,下面程序是客户端部分。

 

老规矩,贴下程序,方便理解:

 

一、继承QObject的socket 客户端程序

MySocketClient::MySocketClient(QObject *parent) : QObject(parent)	
{	
    mp_clsTcpSocket = new QTcpSocket(this);	
}	

	
void MySocketClient::slot_recvServerData()	
{	
    QByteArray data = mp_clsTcpSocket->readAll();	

	
    qDebug() << "------------" << data;	
    qDebug() << "socket recv thread id:" << QThread::currentThreadId();}	

	
void MySocketClient::slot_writeData(QByteArray str)	
{	
    mp_clsTcpSocket->write(str);	
}	

	
void MySocketClient::slot_initSocket()	
{	
    qDebug() << "socket thread id:" << QThread::currentThreadId();	

	
    mp_clsTcpSocket->connectToHost("127.0.0.1",8002);	
    mp_clsTcpSocket->waitForConnected(1000);	

	
    connect(mp_clsTcpSocket,SIGNAL(readyRead()),this,SLOT(slot_recvServerData()));	
}

二、主线程函数

 

①构造函数中使用moveToThread

 m_socketClient.moveToThread(&m_thread);	
    connect(&m_thread, SIGNAL(started()), &m_socketClient, SLOT(slot_initSocket()));	
    m_thread.start();	

	
    connect(this, SIGNAL(signal_sendPicrure(QByteArray)),	
            &m_socketClient,SLOT(slot_writeData(QByteArray)));	
            

 ②主Ui线程通过信号和槽使用线程中的socket发送数据

void Widget::on_pbn_send_clicked()	
{	
    QString str = "i am from server of main ui";	
    emit (signal_sendData(str));	
}

三、程序运行效果:

 

 

640?wx_fmt=png

Server 的初始化在新的线程中(1),接受客户端连接也在新的线程中(2)。

640?wx_fmt=png

Client 的初始化在新的线程中(1),接收服务器数据也在新的线程中(2)。

欢迎大家关注公众号:Pou光明

如需完整程序,后台留下联系方式。

640?wx_fmt=png

  • 5
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值