Qt使用线程的方式有两种,一种是上次所说的继承QThread重新实现run()函数,在run()函数中一直循环处理;另一种则是继承QObject并使用moveToThread()函数将对象移到子线程中。由于继承QThread方式使用的并不规范,Qt官方强烈建议使用继承QObject的方式。
根据之前编写程序得到的结果,在相对复杂的UI设计中,如果socket通信放在住UI中,并且让服务器每间隔10ms发送数据,这样会影响UI的响应,所以应将socket接收数据部分放到线程中。由上次程序得出的结果,使用继承QThread的方式并不可行,所以这次使用继承QObject的形式。经测试得出,继承QObject该方式不会造成UI的卡顿。
下面直接贴段代码压压惊:
客户端.h部分:
#ifndef MYCLIENT_H
#define MYCLIENT_H
#include
#include
class QTcpSocket;
class MyClient : public QObject
{
Q_OBJECT
public:
explicit MyClient(QObject *parent = 0);
bool connectServer();
void writeMsgToServer(QString str);
signals:
public slots:
void slot_readMsgFromServer();
private:
QTcpSocket *mp_clsTcpSocket;
};
#endif // MYCLIENT_H
客户端.cpp部分:
#include "myclient.h"
#include
MyClient::MyClient(QObject *parent) : QObject(parent)
{
mp_clsTcpSocket = new QTcpSocket;
connect(mp_clsTcpSocket, SIGNAL(readyRead()), //Qt::QueuedConnection
this, SLOT(slot_readMsgFromServer()));
}
bool MyClient::connectServer()
{
mp_clsTcpSocket->connectToHost("192.168.18.77",2115);//Qt::BlockingQueuedConnection
if (mp_clsTcpSocket->waitForConnected(1000))
{
qDebug() << "connect success !";
return true;
}else{
qDebug() << "connect faild !";
return false;
}
}
void MyClient::writeMsgToServer(QString str)
{
mp_clsTcpSocket->write(str.toLatin1());
}
void MyClient::slot_readMsgFromServer()
{
QByteArray recMsg = mp_clsTcpSocket->readAll();
qDebug() << "recMsg from Server:" << recMsg;
}
为测试,IP和port直接使用固定的。
UI部分简要程序:
MyClient *mp_clsClient;
QThread *mp_thread;
Widget构造函数部分:
mp_thread= new QThread;
mp_clsClient = new MyClient();
mp_clsClient->connectServer();
mp_clsClient->moveToThread(mp_thread);
StartThread按钮:
mp_thread->start();
Send按钮:
mp_clsClient->writeMsgToServer(ui->lineEdit->text().append("\n"));
结果如图:
服务器端:
以目前我的知识水平来讲,之前在Qt线程中使用socket的方法是不正确的。如果以后遇到新的解决方式,会重新更新!
如果觉得还阔以,请关注~~~