1000字范文,内容丰富有趣,学习的好帮手!
1000字范文 > qint64转为qstring qt_Qt项目中TCP通信的实现方式经验总结(服务端部分)

qint64转为qstring qt_Qt项目中TCP通信的实现方式经验总结(服务端部分)

时间:2022-07-11 04:00:42

相关推荐

qint64转为qstring qt_Qt项目中TCP通信的实现方式经验总结(服务端部分)

总第20篇

本文接第19篇,继续梳理TCP通信过程中的重要知识。本文主要系统地讲解通信服务端部分,以供在以后的项目开发过程中参考。如果觉得不错可以关注专栏面向加薪编程C/C++,第一时间接收文章更新。

1.实现原理

Qt通信过程中,服务端主要是通过QTcpServer创建服务器,监听相应的端口等待客户端连接,当连接成功时可以获得socket描述符,只有拿到了这个socket句柄才可以进行数据传输。 服务器用来检测新连接的信号是newConnection(),在此信号对应的槽中可以对socket进行获取并处理。具体的使用可以参考说明文档,这里示例使用方法如下:

QTcpServer server = new QTcpServer(this);if(server->listen(QHostAddress::Any, 5566){//监听成功时可以绑定信号connect(server, SIGNAL(newConnection()), this, SLOT(SlotNewConnection()));}else{//监听失败做相应的处理}void SlotNewConnection()//监听成功的槽函数,绑定socket相关信号{socket = server->nextPendingConnection();if(socket != NULL){//做相应的处理}connect(socket, SIGNAL(readyRead()), this, SLOT(SlotReadSocket()));connect(socket, SIGNAL(bytesWritten(qint64)), this, SLOT(SlotBytesWritten(qint64)));connect(socket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(SlotDisplayError(QAbstractError::SocketError)));connect(socket, SIGNAL(disconnected()), this, SLOT(SlotDisconnect()));}

linux系统中有自带的延时函数usleep(),在windows平台没有现成的延时函数可用, 这里可以自己写一个,以便全局可调用。

void QtSleep(unsigned int msec){QTime reach_time = QTime::currentTime().addMSecs(msec);while(QTime::currentTime()<reach_time)QCoreApplication::processEvents(QEventLoop::AllEvents, 100);}

2. 传送自定义结构体的方式

Qt中TCP通信时,传输数据最好的方式是使用QDataStream类将其序列化,以二进制的形式传输,读取时也用同样的数据格式,处理比较简单,但是这其中要注意数据在传输的过程中所占用的字节数。具体计算方式,可以参考专栏面向加薪编程C/C++中的文章:在Qt中,如何用QDataStream正确操作QString数据类型。

这里用代码示例socket传输结构体链表的方式。

//结构体定义struct ProcedureMonitorInfo{QString s_procedure_name;QString s_procedure_obj_name;QString s_station_name;QString s_station_obj_name;int n_path_id;int n_station_status;}//下面是传输过程void SlotSendProcedureDataStruct(QList<ProcedureMonitorInfo> procedure_info){QByteArray m_data_block;QDataStream send_procedure(&m_data_block, QIODevice::WriteOnly);send_procedure.setVersion(QDataStream::Qt_4_5);send_procedure<<qint64(0)<<qint64(0)<<qint64(0);send_procedure.device()->seek(0);int struct_length = 0;for(int ii=0; ii<procedure_info.size(); ++ii)struct_length +=(procedure_info.at(ii).s_procedure_name.length() + procedure_info.at(ii).s_procedure_obj_name.length()+procedure_info.at(ii).s_station_name.length()+procedure_info.at(ii).s_station_obj_name.length())*2 + 16 + 8;//打包数据send_procedure<<qint64(_TCP_TUNE_PROCEDURE_)<<qint64(procedure_info.size())<<qint64(struct_length);if(procedure_socket->write(m_data_block)>0) //包头发送成功{for(int j = 0; j<procedure_info.size();++j){QByteArray procedure_data;QDataStream procedure(&procedure_data, QIODevice::WriteOnly);procedure.setVersion(QDataStream::Qt_4_5);procedure<<procedure_info.at(j);procedure_socket->write(procedure_data);}}m_data_block.resize(0);}

3. 多线程的使用

Qt中使用多线程有除通用方法外,还有一种最简便的方法,即是用moveToThread()函数。在Qt内部,已经为此封装了run()函数的事件循环,我们甚至根本不用管详细细节,直接将对象放置进去,对象就运行到另一个线程中了。使用方法如下所示:

QThread *thread = new QThread;threads *thread_slot = new threads;//移动到另一线程thread_slot->moveToThread(thread);thread->start();//两个类之间的相互通信QObject::connect(this, SIGNAL(trans_signal()), thread_slot, SLOT(th_trans_code()));

本文到此结束!

如果对你有帮助,请随手点个赞或点喜欢!随手点赞,手留余香!

=======================================================

欢迎【关注作者、私信作者】。我们一起交流一起进步。

=======================================================

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。