QT TCP服务器和客户端示例程序

devtools/2024/9/20 7:36:54/ 标签: qt, tcp/ip, 服务器

下面是一个简单的 Qt TCP 服务器和客户端示例,演示了如何使用 vSetDrivervSetListenervTcpServerStart 函数。假设 vSetDrivervSetListener 是你定义的自定义函数。

TCP 服务器部分

tcpserver.h
#ifndef TCPSERVER_H
#define TCPSERVER_H#include <QTcpServer>
#include <QTcpSocket>class TcpServer : public QTcpServer
{Q_OBJECT
public:explicit TcpServer(QObject *parent = nullptr);void vSetDriver(QObject *driver);void vSetListener(QObject *listener);void vTcpServerStart(int port);signals:void log(QString message);void connected(quint32 addr, int port);void disconnected(quint32 addr, int port);void recvData(quint32 addr, int port, QByteArray data);protected:void incomingConnection(qintptr socketDescriptor) override;private slots:void onReadyRead();void onDisconnected();private:QObject *m_driver;QObject *m_listener;QTcpSocket *m_socket;
};#endif // TCPSERVER_H

tcpserver.cpp
#include "tcpserver.h"
#include <QHostAddress>TcpServer::TcpServer(QObject *parent) : QTcpServer(parent), m_driver(nullptr), m_listener(nullptr), m_socket(nullptr) {}void TcpServer::vSetDriver(QObject *driver)
{m_driver = driver;
}void TcpServer::vSetListener(QObject *listener)
{m_listener = listener;
}void TcpServer::vTcpServerStart(int port)
{if (!this->listen(QHostAddress::Any, port)) {emit log("Server could not start!");} else {emit log("Server started!");}
}void TcpServer::incomingConnection(qintptr socketDescriptor)
{m_socket = new QTcpSocket(this);connect(m_socket, &QTcpSocket::readyRead, this, &TcpServer::onReadyRead);connect(m_socket, &QTcpSocket::disconnected, this, &TcpServer::onDisconnected);m_socket->setSocketDescriptor(socketDescriptor);emit connected(m_socket->peerAddress().toIPv4Address(), m_socket->peerPort());
}void TcpServer::onReadyRead()
{QByteArray data = m_socket->readAll();emit recvData(m_socket->peerAddress().toIPv4Address(), m_socket->peerPort(), data);
}void TcpServer::onDisconnected()
{emit disconnected(m_socket->peerAddress().toIPv4Address(), m_socket->peerPort());m_socket->deleteLater();
}

TCP 客户端部分

tcpclient.h
#ifndef TCPCLIENT_H
#define TCPCLIENT_H#include <QTcpSocket>class TcpClient : public QObject
{Q_OBJECT
public:explicit TcpClient(QObject *parent = nullptr);void connectToServer(const QString &host, int port);void sendData(const QByteArray &data);signals:void log(QString message);void connected();void disconnected();void recvData(QByteArray data);private slots:void onReadyRead();void onConnected();void onDisconnected();private:QTcpSocket *m_socket;
};#endif // TCPCLIENT_H

tcpclient.cpp
#include "tcpclient.h"TcpClient::TcpClient(QObject *parent) : QObject(parent), m_socket(new QTcpSocket(this))
{connect(m_socket, &QTcpSocket::readyRead, this, &TcpClient::onReadyRead);connect(m_socket, &QTcpSocket::connected, this, &TcpClient::onConnected);connect(m_socket, &QTcpSocket::disconnected, this, &TcpClient::onDisconnected);
}void TcpClient::connectToServer(const QString &host, int port)
{m_socket->connectToHost(host, port);
}void TcpClient::sendData(const QByteArray &data)
{if (m_socket->state() == QAbstractSocket::ConnectedState) {m_socket->write(data);}
}void TcpClient::onReadyRead()
{QByteArray data = m_socket->readAll();emit recvData(data);
}void TcpClient::onConnected()
{emit log("Connected to server");emit connected();
}void TcpClient::onDisconnected()
{emit log("Disconnected from server");emit disconnected();
}

示例主程序

main.cpp
#include <QCoreApplication>
#include "tcpserver.h"
#include "tcpclient.h"int main(int argc, char *argv[])
{QCoreApplication a(argc, argv);TcpServer server;server.vSetDriver(&server);server.vSetListener(&server);server.vTcpServerStart(12345);TcpClient client;client.connectToServer("127.0.0.1", 12345);client.sendData("Hello, Server!");return a.exec();
}

main.pro
QT += core network
CONFIG += console
CONFIG -= app_bundleTEMPLATE = app
SOURCES += main.cpp \tcpserver.cpp \tcpclient.cppHEADERS += tcpserver.h \tcpclient.h

解释

  • TcpServer 类:
    • vSetDrivervSetListener 方法用于设置驱动和监听对象。
    • vTcpServerStart 方法用于启动服务器
    • incomingConnection 方法处理新的连接。
    • onReadyReadonDisconnected 方法分别处理数据接收和连接断开事件。
  • TcpClient 类:
    • connectToServer 方法连接到服务器
    • sendData 方法发送数据。
    • onReadyReadonConnectedonDisconnected 方法分别处理数据接收、连接和断开事件。
  • 主程序
    • 创建并配置服务器和客户端对象。
    • 客户端连接到服务器并发送数据。

这个示例演示了如何使用 Qt 的网络模块创建一个简单的 TCP 服务器和客户端,并展示了如何通过自定义的 vSetDrivervSetListenervTcpServerStart 方法进行初始化和管理。

如何测试:

1. 准备项目结构

确保项目文件结构正确,并包含以下文件:

  • tcpserver.h
  • tcpserver.cpp
  • tcpclient.h
  • tcpclient.cpp
  • main.cpp
  • myproject.pro

2. 项目配置文件 (myproject.pro)

确保你的项目配置文件 (myproject.pro) 正确配置:

QT += core network
CONFIG += console
CONFIG -= app_bundleTEMPLATE = app
SOURCES += main.cpp \tcpserver.cpp \tcpclient.cppHEADERS += tcpserver.h \tcpclient.h

3. 编译项目

使用 qmakemake 编译项目。在终端中执行以下命令:

qmake myproject.pro
make

4. 运行测试

在编译成功后,运行生成的可执行文件。以下是测试步骤:

4.1 启动服务器

在一个终端中运行服务器部分:

./myproject

此时,服务器应该启动并监听端口 12345,等待客户端连接。

4.2 启动客户端

在另一个终端中运行客户端部分:

./myproject

此时,客户端应该连接到服务器并发送 “Hello, Server!” 消息。

5. 验证测试结果

检查服务器输出

服务器应该输出类似以下的日志信息:

Server started!
connect : 127.0.0.1(12345)
recv : 127.0.0.1(12345)

检查客户端输出

客户端应该输出类似以下的日志信息:

Connected to server

6. 修改和扩展

根据需要修改和扩展你的代码。例如,你可以在 recvData 信号处理函数中添加更多的处理逻辑,或者在客户端中添加接收服务器响应的功能。

7. 完整代码示例

tcpserver.h
#ifndef TCPSERVER_H
#define TCPSERVER_H#include <QTcpServer>
#include <QTcpSocket>class TcpServer : public QTcpServer
{Q_OBJECT
public:explicit TcpServer(QObject *parent = nullptr);void vSetDriver(QObject *driver);void vSetListener(QObject *listener);void vTcpServerStart(int port);signals:void log(QString message);void connected(quint32 addr, int port);void disconnected(quint32 addr, int port);void recvData(quint32 addr, int port, QByteArray data);protected:void incomingConnection(qintptr socketDescriptor) override;private slots:void onReadyRead();void onDisconnected();private:QObject *m_driver;QObject *m_listener;QTcpSocket *m_socket;
};#endif // TCPSERVER_H

tcpserver.cpp
#include "tcpserver.h"
#include <QHostAddress>TcpServer::TcpServer(QObject *parent) : QTcpServer(parent), m_driver(nullptr), m_listener(nullptr), m_socket(nullptr) {}void TcpServer::vSetDriver(QObject *driver)
{m_driver = driver;
}void TcpServer::vSetListener(QObject *listener)
{m_listener = listener;
}void TcpServer::vTcpServerStart(int port)
{if (!this->listen(QHostAddress::Any, port)) {emit log("Server could not start!");} else {emit log("Server started!");}
}void TcpServer::incomingConnection(qintptr socketDescriptor)
{m_socket = new QTcpSocket(this);connect(m_socket, &QTcpSocket::readyRead, this, &TcpServer::onReadyRead);connect(m_socket, &QTcpSocket::disconnected, this, &TcpServer::onDisconnected);m_socket->setSocketDescriptor(socketDescriptor);emit connected(m_socket->peerAddress().toIPv4Address(), m_socket->peerPort());
}void TcpServer::onReadyRead()
{QByteArray data = m_socket->readAll();emit recvData(m_socket->peerAddress().toIPv4Address(), m_socket->peerPort(), data);
}void TcpServer::onDisconnected()
{emit disconnected(m_socket->peerAddress().toIPv4Address(), m_socket->peerPort());m_socket->deleteLater();
}

tcpclient.h
#ifndef TCPCLIENT_H
#define TCPCLIENT_H#include <QTcpSocket>class TcpClient : public QObject
{Q_OBJECT
public:explicit TcpClient(QObject *parent = nullptr);void connectToServer(const QString &host, int port);void sendData(const QByteArray &data);signals:void log(QString message);void connected();void disconnected();void recvData(QByteArray data);private slots:void onReadyRead();void onConnected();void onDisconnected();private:QTcpSocket *m_socket;
};#endif // TCPCLIENT_H


http://www.ppmy.cn/devtools/52338.html

相关文章

vue脚手架 笔记07

01 手动搭建vuex vuex叫做全局状态管理仓库 vuex的搭建: 1.下载vuex3.x版本 npm i vuex3.0.0 --save 2. 在src/store下面创建index.js 3.引入vue和vuex import Vue from vue import Vuex from vuex Vue.use(Vuex) 4.export default new Vuex.Store({ 五大属性 state mutatio…

apache poi excel export

apache poi excel export 水一篇 凑个数&#xff08;啊 水文章好羞耻啊&#xff01;请原谅我私密马赛&#xff01;&#xff09; 1 ExcelColumn Data Builder ToString NoArgsConstructor AllArgsConstructor public class ExcelColumn implements Serializable {Serialprivat…

齐普夫定律在循环神经网络中的语言模型的应用

目录 齐普夫定律解释公式解释图与公式的关系代码与图的分析结论 使用对数表达方式的原因1. 线性化非线性关系2. 方便数据可视化和分析3. 降低数值范围4. 方便参数估计公式详细解释结论 来自&#xff1a;https://zh-v2.d2l.ai/chapter_recurrent-neural-networks/language-model…

JAVA 策略模式使用spring托管其实现类

上一篇的“JAVA 替代SWITCH 枚举值 CASE 的 策略模式 ” 中使用new关键字实例化一个类时&#xff0c;这个类的实例不由Spring容器管理&#xff0c;因此Autowired注解在这个实例中不会生效。Spring的依赖注入功能仅对其管理的bean有效&#xff0c;即那些通过Spring容器创建和管理…

安卓实现圆形按钮轮廓以及解决无法更改按钮颜色的问题

1.实现按钮轮廓 在drawable文件新建xml文件 <shape xmlns:android"http://schemas.android.com/apk/res/android"<!--实现圆形-->android:shape"oval"><!--指定内部的填充色--><solid android:color"#FFFFFF"/><!-…

Mysql知识点

1. 二叉树 1.1 什么是B-树 B树又名平衡多路查找树&#xff08;也把B树称为B-树&#xff09;查找路径不只两个&#xff0c;不同于常见的二叉树&#xff0c;它是一种多叉树&#xff0c;我们常见的使用场景一般是在数据库索引技术里&#xff0c;大量使用者B树和B树的数据结构。 …

HTML静态网页成品作业(HTML+CSS)—— 名人霍金介绍网页(6个页面)

&#x1f389;不定期分享源码&#xff0c;关注不丢失哦 文章目录 一、作品介绍二、作品演示三、代码目录四、网站代码HTML部分代码 五、源码获取 一、作品介绍 &#x1f3f7;️本套采用HTMLCSS&#xff0c;未使用Javacsript代码&#xff0c;共有6个页面。 二、作品演示 三、代…

Django后台忘记管理员的账号

使用命令启动项目&#xff1a; python manage.py runserver输入后缀/admin&#xff0c;进入后台管理员&#xff0c;如果此时忘记你先前设置的用户名与密码怎么办&#xff1f; 终端输入&#xff1a; python manage.py shell 输入以下内容&#xff0c;并查看返回结果&#xff…

我在高职教STM32——GPIO入门之蜂鸣器

大家好&#xff0c;我是老耿&#xff0c;高职青椒一枚&#xff0c;一直从事单片机、嵌入式、物联网等课程的教学。对于高职的学生层次&#xff0c;同行应该都懂的&#xff0c;老师在课堂上教学几乎是没什么成就感的。正因如此&#xff0c;才有了借助 CSDN 平台寻求认同感和成就…

【交易策略】#22-24 残差资金流强度因子

【交易策略】#22-24 残差资金流强度因子

多模态LLM 跨越语言与视觉的边界

一、引言 在数字时代的浪潮中&#xff0c;我们被由语言和视觉等多种模态构成的信息海洋所包围。人类大脑以其卓越的多模态上下文理解能力&#xff0c;在日常任务中游刃有余。然而&#xff0c;在人工智能领域&#xff0c;如何将这种能力赋予机器&#xff0c;尤其是如何在语言模…

RabbitMQ实践——监控行为事件

大纲 启用Event Exchange创建队列绑定队列和Event Exchange测试参考资料 在之前的章节中&#xff0c;我们基本都是在管理后台创建“队列”&#xff08;Queue&#xff09;、“交换器”&#xff08;Exchange&#xff09;和“绑定关系”&#xff08;Banding&#xff09;。实际上&a…

数据可视化实验一:Panda数据处理及matplotlib绘图初步

目录​​​​​​​ 2024-6-17 一、请将所有含有发明家“吴峰”的发明专利的“申请日”打印出来。并将含有“吴峰”的所有发明专利条目保存到Excel中 1.1 代码实现 1.2 运行结果 二、读取文件创建城市、人口、性别比、城镇化率DataFrame对象&#xff0c;计算指标排名&…

⭐ ▶《强化学习的数学原理》(2024春)_西湖大学赵世钰 Ch3 贝尔曼最优公式 【压缩映射定理】

PPT 截取必要信息。 课程网站做习题。总体 MOOC 过一遍 1、视频 学堂在线 习题 2、过 电子书&#xff0c;补充 【下载&#xff1a;本章 PDF 电子书 GitHub 界面链接】 [又看了一遍视频] 3、总体 MOOC 过一遍 习题 学堂在线 课程页面链接 中国大学MOOC 课程页面链接 B 站 视频链…

2024-06-10 问AI: 在大语言模型中,ReAct Agents的理论基础是什么

文心一言 在大语言模型中&#xff0c;ReAct Agents的理论基础主要基于以下几个关键点&#xff1a; 推理与行为的结合&#xff1a;ReAct框架的核心思想是将大型语言模型的推理能力和行为能力相结合。这种结合使得模型能够以交错的方式生成推理步骤和特定于任务的操作&#xff0c…

嵌入式技术学习——c51——串口

一、串口介绍。 串口是一个 通讯接口。成本低&#xff0c;容易使用&#xff0c;通信线路简单&#xff0c;可实现两个设备的相互通信 单片机的串口可以实现单片机于单片机&#xff0c;单片机与电脑&#xff0c;单片机与其他模块相互通信。 51单片机内部自带UART&#xff0c;通…

【运维自动化-配置平台】如何使用云资源同步功能(腾讯云为例)

云资源同步是通过apikey去单向同步云上的主机资源和云区域信息&#xff0c;目前支持腾讯云和亚马逊云。主要特性 1、蓝鲸配置平台周期性的单向只读同步云主机和vpc&#xff08;对应蓝鲸云区域&#xff09;信息&#xff0c;第一次全量&#xff0c;后面增量 2、默认同步到主机池…

「前端+鸿蒙」鸿蒙应用开发-ArkTS语法说明-组件声明

ArkTS 是鸿蒙应用开发中的一个框架,它允许开发者使用 TypeScript 语法来创建声明式的用户界面。在 ArkTS 中,组件声明是构建 UI 的基础。以下是 ArkTS 快速入门的指南,包括组件声明的语法说明和示例代码。 ArkTS 快速入门 - 语法说明 - 组件声明 组件基础 在 ArkTS 中,组…

C++ day3

widget样式表 *{background-color: rgb(255, 255, 255); } QFrame#frame{border-radius:25px;border-image: url(:/Logo/shanChuan.jpg); }#frame_2{border-radius:25px;background-color: rgba(154, 154, 154, 120); } QLabel#label{border-radius:25px;background-color: rg…