当前位置: 首页 > article >正文

Qt网络通信(TCP/UDP)

目录

一、TCP通信

1.QTcpServer

2.QTcpSocket

3.TCP通信基本流程

4.示例

二、UDP通信

1.QUdpSocket

2.UDP通信基本流程

3.发送形式

4.示例


   

一、TCP通信

QTcpServer和QTcpSocket是Qt中用于实现TCP通信的两个类。

1.QTcpServer

QTcpServer类用于创建TCP服务器,监听指定端口,等待客户端连接。

①常用监听接口:

  • listen():开始监听指定的IP地址和端口,返回是否监听成功。
  • isListening():返回服务器是否处于监听状态。

②常用连接接口:

  • nextPendingConnection():在槽函数中调用,用于获取与新连接的客户端对应的QTcpSocket对象。
  • close():停止监听。

③QTcpServer常用信号:

  • newConnection:当有新的客户端连接时,会发射该信号。
  • acceptError(socketError):当接受一个新的连接时发生了错误,就发射此信号,参数socketError描述错误信息。

   

2.QTcpSocket

QTcpSocket类用于建立TCP连接并进行数据传输,既可以作为客户端连接服务器,也可以作为服务器端与客户端通信。

①常用连接接口:

  • connectToHost():用于连接到指定的服务器,支持异步连接,连接成功后会发射connected信号。
  • waitForConnected():阻塞式连接函数,等待连接成功或失败后才返回。
  • disconnectFromHost():断开与主机的连接。

②常用数据传输接口:

  •  write():向连接端写入数据。
  • read()readAll():用于从接收缓冲区读取数据。当有新数据进入缓冲区时,会发射readyRead信号。

③常用状态获取接口:

  • state():获取当前套接字的状态。
  • peerAddress()peerPort():获取连接端的IP地址和端口号。

④QTcpSocket常用信号:

  • connected:当连接成功建立时,发射该信号。
  • disconnected:当连接断开时,发射该信号。
  • readyRead:当有数据可读时,发射该信号。
  • errorOccurred(socketError):当连接发生错误时,发射该信号。

  

3.TCP通信基本流程

服务器端:

创建QTcpServer对象---启动服务器监听---处理新连接请求---数据传输---关闭连接

  1. 创建QTcpServer对象,用于监听客户端的连接请求。
  2. 调用QTcpServer对象的listen()函数,指定要监听的IP地址和端口号,开始监听客户端的连接请求。
  3. 当有客户端的连接请求时,QTcpServer会发射newConnection信号。在对应的槽函数中,调用nextPendingConnection()函数可以获取与客户端连接的QTcpSocket对象。
  4. 通过获取到的QTcpSocket对象,可以使用write()函数向客户端发送数据,当有新数据可读时,QTcpSocket会发射readyRead信号,在对应的槽函数中可以使用read()或readAll()函数读取客户端发送的数据。
  5. 当通信结束时,调用QTcpSocket的close()函数关闭与客户端的连接。

客户端:

创建QTcpSocket对象---连接服务器---数据传输---关闭连接

  1. 创建QTcpSocket对象,用于与服务器进行通信。
  2. 调用QTcpSocket的connectToHost()函数,指定服务器的IP地址和端口号,发起连接请求。
  3. 连接成功后,可以使用write()函数向服务器发送数据,当有新数据可读时,QTcpSocket会发射readyRead信号,在对应的槽函数中可以使用read()或readAll()函数读取服务器发送的数据。
  4. 当通信结束时,调用QTcpSocket的close()函数关闭与服务器的连接。

   

4.示例

服务器端主要代码:

QTcpServer *m_server;
QTcpSocket *m_tcp;

m_server = new QTcpServer(this);

//设置服务器监听
quint16 port = 9999;
m_server->listen(QHostAddress::Any,port);
qDebug()<<"服务器已启动!";

//检测新的客户端连接
connect(m_server,&QTcpServer::newConnection,this,[=]{
    m_tcp = m_server->nextPendingConnection();
    qDebug()<<"成功和客户端连接...";
    
    //检测客户端数据
    connect(m_tcp,&QTcpSocket::readyRead,this,[=]{
        QString str = m_tcp->readAll();
        qDebug()<<"客户端:"<<str;
    });
    
    //检测客户端断开连接
    connect(m_tcp,&QTcpSocket::disconnected,this,[=]{
        qDebug()<<"客户端断开连接...";
        m_tcp->deleteLater();
    });
});

//发送数据
QString str = "message";
m_tcp->write(str.toUtf8());
qDebug()<<"服务器:"<<str;

客户端主要代码:

QTcpSocket *m_tcp;

m_tcp = new QTcpSocket(this);

//连接服务器
QString ip = "127.0.0.1";
quint16 port = 9999;
m_tcp->connectToHost(QHostAddress(ip),port);

//检测和服务器成功连接
connect(m_tcp,&QTcpSocket::connected,this,[=]{
    qDebug()<<"服务器连接成功!";
});

//检测和服务器断开连接
connect(m_tcp,&QTcpSocket::disconnected,this,[=]{
    qDebug()<<"服务器断开连接...";
});

//检测服务器数据
connect(m_tcp,&QTcpSocket::readyRead,this,[=]{
    QString str = m_tcp->readAll();
    qDebug()<<"服务器:"+str;
});

//发送数据
QString str = "message";
m_tcp->write(str.toUtf8());
qDebug()<<"客户端:"+str;

//断开连接
m_tcp->close();

参考:

基于TCP的Qt网络通信 | 爱编程的大丙

  


   

二、UDP通信

在Qt中进行UDP通信主要通过QUdpSocket类来实现。

1.QUdpSocket

①常用接口:

  • bind():用于将套接字绑定到指定的本地地址和端口,以便接受数据报。
  • joinMulticastGroup():让套接字加入多播组以接收多播数据。
  • leaveMulticastGroup():让套接字离开多播组。
  • pendingDatagramSize():返回下一个可读数据报大小,便于读取准备。
  • readDatagram():读取数据报并存入缓冲区,同时可获取发送方的地址和端口信息。
  • writeDatagram():向指定的地址和端口发送数据报。

②常用信号:

  • readyRead:当有数据报可读时发出信号,通知程序可以读取数据。
  • stateChanged:套接字状态改变时发出,可据此处理状态相关逻辑。
  • error:套接字发生错误时发出,便于错误处理。

   

2.UDP通信基本流程

发送端:

创建套接字---发送数据---关闭套接字

  1. 使用QUdpSocket类创建一个UDP套接字对象。
  2. 使用writeDatagram()函数发送数据报,指定目标IP地址和端口号。
  3. 在数据发送完成后,关闭套接字以释放资源。

接收端:

创建套接字---绑定端口---接收数据---关闭套接字

  1. 使用QUdpSocket类创建一个UDP套接字对象。
  2. 使用bind函数绑定本地端口,用于接收数据报。
  3. 当有数据报到达时,readyRead信号会被触发,在对应的槽函数中使用readDatagram()函数读取数据。
  4. 在数据接收完成后,关闭套接字以释放资源。

   

3.发送形式

单播:发送端向一个特定的接收端发送数据,需要指定接收端的IP地址和端口号。

QUdpSocket socket;
socket.writeDatagram(data, QHostAddress("192.168.1.100"), 7777);

广播:将数据报发送到广播地址,同一网络中的所有设备都会接收到广播数据报,但只有那些运行了相应接收程序并监听特定端口的设备才会处理这些数据报。

QUdpSocket socket;
socket.writeDatagram(data, QHostAddress::Broadcast, 7777);

组播:加入组播组后发送数据报,只有组内成员能接收。

QUdpSocket socket;
socket.joinMulticastGroup(QHostAddress("224.0.0.100"));
socket.writeDatagram(data, QHostAddress("224.0.0.100"), 7777);

   

4.示例

QUdpSocket *m_udp;

m_udp = new QUdpSocket(this);

//绑定本地端口
quint16 port = 8888;
if(m_udp->bind(port))
    qDebug()<<"已成功绑定:"+QString::number(m_udp->localPort());
else
    qDebug()<<"绑定失败";
//bind(port,QAbstractSocket::ReuseAddressHint)
//使套接字能尝试重新绑定已被占用的地址和端口

//检测是否有数据报可读
connect(m_udp,&QUdpSocket::readyRead,this,[=]{
    while (m_udp->hasPendingDatagrams()) {
        QByteArray buffer;
        buffer.resize(m_udp->pendingDatagramSize());
        QHostAddress tar_ip;
        quint16 tar_port;
        m_udp->readDatagram(buffer.data(),buffer.size(),&tar_ip,&tar_port);
        QString str = QString("[%1-%2]: ").arg(tar_ip.toString()).arg(tar_port);
        str += buffer.data();
        qDebug()<<str;
    }
});
/*如果不使用while循环,当有多个数据报等待处理时,
每次调用m_udp->readDatagram只会读取一个数据报。*/

//单播
QString tar_ip = "127.0.0.1";
quint16 tar_port = 8888;
QString str = "message";
m_udp->writeDatagram(str.toUtf8(),QHostAddress(tar_ip),tar_port);
qDebug()<<"[out]: "<<str;

//广播
quint16 tar_port = 8888;
QString str = "message";
m_udp->writeDatagram(str.toUtf8(),QHostAddress::Broadcast,tar_port);
qDebug()<<"[broadcast]: "<<str;

   


http://www.kler.cn/a/519492.html

相关文章:

  • BLE透传方案,IoT短距无线通信的“中坚力量”
  • 【ARM】解决MDK在打开工程的时候提示CMSIS的版本不对问题
  • FreeRtos的使用教程
  • 为AI聊天工具添加一个知识系统 之69 详细设计 之10 三种中台和时间度量 之2
  • 计算机的错误计算(二百二十二)
  • 第17篇:python进阶:详解数据分析与处理
  • 运维实战---多种方式在Linux中部署并初始化MySQL
  • DeepSeek_R1论文翻译稿
  • RV1126画面质量五:Profile和编码等级讲解
  • 【北京大学 凸优化】Lec1 凸优化问题定义
  • Linux Futex学习笔记
  • 第 10 课 Python 内置函数
  • 在 Ubuntu22.04 上安装 Splunk
  • 2025年1月22日(什么是扫频)
  • vue router路由复用及刷新问题研究
  • 从 VJ 拥塞控制到 BBR:ACK 自时钟和 pacing
  • 《Kotlin核心编程》上篇
  • 【动态规划】杨表
  • YOLOv11改进,YOLOv11检测头融合DSConv(动态蛇形卷积),并添加小目标检测层(四头检测),适合目标检测、分割等任务
  • SQL注入漏洞之SQL注入基础知识点 如何检测是否含有sql注入漏洞
  • 【leetcode100】二叉树的层序遍历
  • Elasticsearch中的度量聚合:深度解析与实战应用
  • mock可视化生成前端代码
  • javascript-es6 (一)
  • 【Vim】Vim 中将文件内容复制到系统剪切板的方法
  • 基于Oracle 19C的ADVM与ACFS标准化实施文档