Qt|QTcpServer多个TcpSocket连接
//connection类
#ifndef CONNECTION_H
#define CONNECTION_H
#include
#include
#include
#include
#include
#include class Connection:public QObject
{
Q_OBJECT
public:
int m_nSocketID;
//-1 indicate the socket is invalid;
else is the global id of the connection
int m_nMsgReceived;
int m_nMsgSent;
QTcpSocket* m_pTcpSocket;
public:
Connection(){m_nSocketID = -1;
}
~Connection()
{
if (m_pTcpSocket!=NULL)
{
delete m_pTcpSocket;
}
}
public:
void InitializeConnection(QTcpSocket* socket, int id)
{
m_pTcpSocket = socket;
m_pTcpSocket->setParent(this);
m_nMsgReceived = 0;
m_nMsgSent = 0;
m_nSocketID = id;
}
void DeleteConnection()
{
m_nSocketID = -1;
m_pTcpSocket->disconnect();
// delete m_pTcpSocket;
若delete会报错, ?
m_pTcpSocket = NULL;
}
};
#endif
//server.h
#ifndef SERVER_H
#define SERVER_H#include
#include
#include
#include
#include
#include
#include
#include "ui_base.h"
#include "qtheader.h"
#include "Connection.h"class Server : public QMainWindow
{
Q_OBJECT
public:
Server(QWidget *parent = 0, Qt::WFlags flags = 0);
~Server();
private:
Ui::BaseClass ui;
public://public variables
QTcpServer* m_pTcpServer;
Connection* m_pConnection;
QMutex m_mutexConnection;
//mutex to protect the array
int m_nConnected;
int m_nID;
public:
bool InitializeServers();
void ShowStatusMessage(const QString str);
public slots:
void OnNewConnection();
void OnReadyRead();
void OnDisconnected();
}#endif
//server.cpp
/*! @function
********************************************************************************
Function : Server
Desc: constructor of the Server class, initialize the servers and variables
Params:
Return:
Exception:
--------------------------------------------------------------------------------
Notes:
Examples :
--------------------------------------------------------------------------------
Author:
*******************************************************************************/
Server::Server(QWidget *parent, Qt::WFlags flags)
: QMainWindow(parent, flags)
{
ui.setupUi(this);
m_nSurveillanceID = 1;
m_nConnected = 0;
m_pConnection = new Connection[10];
if (!InitializeServers())
{
exit(-1);
}
}/*! @function
********************************************************************************
Function : ~Server
Desc:
Params:
Return:
Exception:
--------------------------------------------------------------------------------
Notes:
Examples :
--------------------------------------------------------------------------------
Author:
*******************************************************************************/
Server::~Server()
{
//ShowMessageBox("test");
delete m_pConnection;
}
/*! @function
********************************************************************************
Function : InitializeServers
Desc: initialize all the servers
Params:
Return:
if any initialization of the server failed, return false
Exception:
--------------------------------------------------------------------------------
Notes:
Examples :
--------------------------------------------------------------------------------
Author:
*******************************************************************************/
bool Server::InitializeServers()
{
m_pTcpServer = new QTcpServer(this);
if (!m_pTcpServer->listen(QHostAddress("192.168.1.100"), 8745))
{
ShowMessageBox("server listen to 8745 error, exiting...");
return (false);
}
else
{
connect(m_pTcpServer, SIGNAL(newConnection()), this, SLOT(OnNewConnection()));
}
return true;
}/*! @function
********************************************************************************
Function : OnNewConnection
Desc: slot function, if there is new connection request, this function is called
Params:
Return:
Exception:
--------------------------------------------------------------------------------
Notes:
Examples :
--------------------------------------------------------------------------------
Author:
*******************************************************************************/
void Server::OnNewConnection()
{
//check how many connections established
ShowStatusMessage("new connection...");
//find one connection to store the new connection
int i=0;
for (i=0;
i<10;
i++)
{
if (m_pConnection[i].m_nSocketID == -1)
{
break;
}
} //add new connection
m_mutexConnection.lock();
(m_pConnection[i]).InitializeConnection(m_pTcpServer->nextPendingConnection(), m_nID);
connect(m_pConnection[i].m_pTcpSocket, SIGNAL(readyRead()), this, SLOT(OnReadyRead()));
connect(m_pConnection[i].m_pTcpSocket, SIGNAL(disconnected()), this, SLOT(OnDisconnected()));
m_mutexConnection.unlock();
//set the flags
m_nID++;
m_nConnected++;
//if the connection is 10, close the server
if (m_nConnected==10)
{
m_pTcpServer->close();
ShowStatusMessage("Maximum connection (10) reached, new connection will be refused......");
}
}
/*! @function
********************************************************************************
Function : OnReadyRead
Desc: slot function, if new data is available for server, this function is called
Params:
Return:
Exception:
--------------------------------------------------------------------------------
Notes:
Examples :
--------------------------------------------------------------------------------
Author:
*******************************************************************************/
void Server::OnReadyRead()
{}
/*! @function
********************************************************************************
Function : OnDisconnected
Desc: slot function, if the socket is disconnected from the server this function is called
Params:
Return:
Exception:
--------------------------------------------------------------------------------
Notes:
Examples :
--------------------------------------------------------------------------------
Author:
*******************************************************************************/
void Server::OnDisconnected()
{
//get the connection that disconnected from the server
QTcpSocket* socket = qobject_cast(sender());
Connection* connection = qobject_cast(socket->parent());
//delete the connection
m_mutexConnection.lock();
connection->DeleteConnection();
m_mutexConnection.unlock();
ShowStatusMessage("server disconnected");
m_nSurveillanceConnected--;
//if the connection is reduced from 10 to 9, reopen the server, listen
if (m_nSurveillanceConnected==9)
{
m_pTcpServerSurveillance->listen(QHostAddress("192.168.1.100"), 8745);
}
}
/*! @function
********************************************************************************
Function : ShowStatusMessage
Desc: show the message on the status bar
Params:
[IN] const QString str, the message to show
Return:
Exception:
--------------------------------------------------------------------------------
Notes: the status bar will be cleared first.
Examples :
--------------------------------------------------------------------------------
Author:
*******************************************************************************/
void Server::ShowStatusMessage(const QString str)
{
this->ui.statusBar->clearMessage();
this->ui.statusBar->showMessage(str);
}
几个问题简单说明:
1.这个不见得能够直接使用,是从我完整的程序中取出的一部分,根据需要再做调整;
2.这里为什么用的值指针保存connection,而不用list,vector等:
【Qt|QTcpServer多个TcpSocket连接】首先看看继承关系:QObject->QIODevice->QAbstractSocket->QTcpSocket,对于QObject这个类来说,是不能copy的,而从其派生的类也是同样不能复制的。如果使用list或vector,会调用到类似push_back这样的函数,其本质是复制,编译会报错的。这里就采用指针来解决这个问题。
推荐阅读
- Android|Android install 多个设备时指定设备
- K8S|K8S 生态周报| Istio 即将发布重大安全更新,多个版本受影响
- 如何将多个小分子文件合并为单个
- 参与设计20多个区块链经济系统,我总结出4个原则和7个陷阱
- java多线程-锁
- 后台|NATAPP内网穿透通过nginx实现一个端口访问多个不同端口服务
- tomcat|tomcat配置多个项目的server.xml的配置
- js.12
- python|读取多个子文件夹中的多张图片
- 同时注册多个|同时注册多个 vue 自定义指令 —— require.context