通过QT进行服务器和客户端之间的网络通信
客户端
client.pro
#-------------------------------------------------
#
# Project created by QtCreator 2024-07-02T14:11:20
#
#-------------------------------------------------QT += core gui network #网络通信greaterThan(QT_MAJOR_VERSION, 4): QT += widgetsTARGET = client
TEMPLATE = app# The following define makes your compiler emit warnings if you use
# any feature of Qt which as been marked as deprecated (the exact warnings
# depend on your compiler). Please consult the documentation of the
# deprecated API in order to know how to port your code away from it.
DEFINES += QT_DEPRECATED_WARNINGS# You can also make your code fail to compile if you use deprecated APIs.
# In order to do so, uncomment the following line.
# You can also select to disable deprecated APIs only up to a certain version of Qt.
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000 # disables all the APIs deprecated before Qt 6.0.0SOURCES += main.cpp\widget.cppHEADERS += widget.hFORMS += widget.ui
widget.h
#ifndef WIDGET_H
#define WIDGET_H#include <QWidget>
#include <QTcpSocket>namespace Ui {
class Widget;
}class Widget : public QWidget
{Q_OBJECTpublic:explicit Widget(QWidget *parent = 0);~Widget();void InitClient();private slots:void on_connect_bt_clicked();void on_send_bt_clicked();void OnReadData();private:Ui::Widget *ui;QTcpSocket *m_pSocket;
};#endif // WIDGET_H
main.cpp
#include "widget.h"
#include <QApplication>int main(int argc, char *argv[])
{QApplication a(argc, argv);Widget w;w.InitClient();w.show();return a.exec();
}
widget.cpp
#include "widget.h"
#include "ui_widget.h"
#include <QDebug> //Qt 提供的输出调试信息的工具。
#include <QHostAddress>Widget::Widget(QWidget *parent) : //Widget类继承自QWidgetQWidget(parent),ui(new Ui::Widget) //通过ui对象初始化界面布局
{ui->setupUi(this);m_pSocket = NULL; //初始化m_pSocket为NULL
}Widget::~Widget() //析构函数释放了ui对象。
{delete ui;
}void Widget::InitClient() //设置界面初始状态,创建串口对象
{qDebug() << "Widget::InitClient() enter";if (NULL == m_pSocket){m_pSocket = new QTcpSocket(this); //QTcpSocket是Qt提供的用于TCP网络通信的类connect(m_pSocket, SIGNAL(readyRead()), this, SLOT(OnReadData()));//readyRead()当socket接收到新的数据时发出的信号,SIGNAL()是一个宏,将信号转换为字符串形式。this是信号的发送者。//当m_pSocket对象接收到数据时,会触发readyRead()信号,然后调用当前类的OnReadData()槽函数来处理这些接收到的数据}qDebug() << "Widget::InitClient() exit";
}void Widget::on_connect_bt_clicked() //当按钮connect_bt被点击时触发
{qDebug() << "Widget::on_connect_bt_clicked() enter";QString strIP = ui->ip_edit->text(); //获取用户输入的IP地址QString strPort = ui->port_edit->text();qDebug() << strIP << " " << strPort;if (strIP.length() == 0 || strPort.length() == 0) //检查用户输入的有效性,如果IP或端口号为空,则输出错误信息并返回{qDebug() << "input error";return;}if (NULL == m_pSocket) //检查m_pSocket是否为NULL,如果是则输出错误信息并返回{qDebug() << "socket error";return;}m_pSocket->connectToHost(QHostAddress("127.0.0.1"), strPort.toShort());//使用m_pSocket->connectToHost()连接到指定的主机地址(这里是本地地址 "127.0.0.1")和端口号if (m_pSocket->waitForConnected(3000))//使用m_pSocket->waitForConnected(3000)等待连接建立,超时时间为3000毫秒(3秒){qDebug() << "connect ok";}else{qDebug() << "connect error";}qDebug() << "Widget::on_connect_bt_clicked() exit";
}void Widget::on_send_bt_clicked()
{qDebug() << "Widget::on_send_bt_clicked() enter";QString strData = ui->send_edit->text();if (strData.length() == 0){qDebug() << "input error";return;}if (NULL == m_pSocket){qDebug() << "socket error";return;}m_pSocket->write(strData.toStdString().data()); //发送字符串形式的数据到已连接的服务器端qDebug() << "Widget::on_send_bt_clicked() exit";
}void Widget::OnReadData()
{QByteArray arr = m_pSocket->readAll(); //读取所有接收到的数据,并将其存储arr中qDebug() << arr;
}
widget.ui

<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0"><class>Widget</class><widget class="QWidget" name="Widget"><property name="geometry"><rect><x>0</x><y>0</y><width>692</width><height>468</height></rect></property><property name="windowTitle"><string>Widget</string></property><widget class="QLabel" name="label"><property name="geometry"><rect><x>50</x><y>60</y><width>72</width><height>15</height></rect></property><property name="text"><string>ip</string></property></widget><widget class="QLineEdit" name="ip_edit"><property name="geometry"><rect><x>100</x><y>60</y><width>181</width><height>21</height></rect></property></widget><widget class="QLabel" name="label_2"><property name="geometry"><rect><x>40</x><y>100</y><width>72</width><height>15</height></rect></property><property name="text"><string>port</string></property></widget><widget class="QLineEdit" name="port_edit"><property name="geometry"><rect><x>100</x><y>100</y><width>181</width><height>21</height></rect></property></widget><widget class="QPushButton" name="connect_bt"><property name="geometry"><rect><x>350</x><y>90</y><width>93</width><height>28</height></rect></property><property name="text"><string>connect</string></property></widget><widget class="QPushButton" name="send_bt"><property name="geometry"><rect><x>350</x><y>150</y><width>93</width><height>28</height></rect></property><property name="text"><string>send</string></property></widget><widget class="QLineEdit" name="send_edit"><property name="geometry"><rect><x>100</x><y>160</y><width>181</width><height>21</height></rect></property></widget></widget><layoutdefault spacing="6" margin="11"/><resources/><connections/>
</ui>
服务器
server.pro
#-------------------------------------------------
#
# Project created by QtCreator 2024-07-02T09:20:48
#
#-------------------------------------------------QT += core gui networkgreaterThan(QT_MAJOR_VERSION, 4): QT += widgetsTARGET = server
TEMPLATE = app# The following define makes your compiler emit warnings if you use
# any feature of Qt which as been marked as deprecated (the exact warnings
# depend on your compiler). Please consult the documentation of the
# deprecated API in order to know how to port your code away from it.
DEFINES += QT_DEPRECATED_WARNINGS# You can also make your code fail to compile if you use deprecated APIs.
# In order to do so, uncomment the following line.
# You can also select to disable deprecated APIs only up to a certain version of Qt.
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000 # disables all the APIs deprecated before Qt 6.0.0SOURCES += main.cpp\widget.cppHEADERS += widget.hFORMS += widget.ui
widget.h
#ifndef WIDGET_H
#define WIDGET_H#include <QWidget>
#include <QTcpServer>namespace Ui {
class Widget;
}class Widget : public QWidget
{Q_OBJECTpublic:explicit Widget(QWidget *parent = 0);~Widget();void InitServer();private slots:void OnNewConnection();void OnReadyData();void on_listen_bt_clicked();private:Ui::Widget *ui;QTcpServer *m_pServer;
};#endif // WIDGET_H
main.cpp
#include "widget.h"
#include <QApplication>int main(int argc, char *argv[])
{QApplication a(argc, argv);Widget w;w.InitServer();w.show();return a.exec();
}
widget.cpp
#include "widget.h"
#include "ui_widget.h"
#include <QDebug>
#include <QHostAddress>
#include <QTcpSocket>Widget::Widget(QWidget *parent) :QWidget(parent),ui(new Ui::Widget)
{ui->setupUi(this);m_pServer = NULL;
}Widget::~Widget()
{delete ui;
}void Widget::InitServer()
{qDebug() << "Widget::InitServer() enter";if (NULL == m_pServer){m_pServer = new QTcpServer(this);connect(m_pServer, SIGNAL(newConnection()), this, SLOT(OnNewConnection()));}qDebug() << "Widget::InitServer() exit";
}void Widget::OnNewConnection()
{qDebug() << "new connection";QTcpSocket *pTmp = m_pServer->nextPendingConnection(); //获取下一个挂起的连接if (NULL != pTmp){connect(pTmp, SIGNAL(readyRead()), this, SLOT(OnReadyData()));//当这个客户端socket有数据可读时,就会调用OnReadyData()函数}
}void Widget::OnReadyData()
{qDebug() << "read data";QTcpSocket *pTmp = (QTcpSocket *)sender(); //获取信号的发送者if (NULL == pTmp){qDebug() << "socket error";return;}QByteArray arr = pTmp->readAll(); //读取所有接收到的数据//qDebug() << arr;QString strData = ui->textEdit->toPlainText(); //将接收到的数据显示在界面中strData.append("recv : "); //追加数据recv :strData.append(arr);strData.append("\n");ui->textEdit->setText(strData);pTmp->write(arr); //将接收到的数据原样发送回客户端
}void Widget::on_listen_bt_clicked()
{qDebug() << "Widget::on_listen_bt_clicked() enter";if (NULL == m_pServer){return;}QString strIP = ui->ip_edit->text();QString strPort = ui->port_edit->text();if (strIP.length() == 0 || strPort.length() == 0){qDebug() << "input error";return;}bool bRet = m_pServer->listen(QHostAddress(strIP), strPort.toShort()); //监听指定的IP地址和端口号if (bRet == true){qDebug() << "server listen ok";}qDebug() << "Widget::on_listen_bt_clicked() enter";
}
widget.ui

<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0"><class>Widget</class><widget class="QWidget" name="Widget"><property name="geometry"><rect><x>0</x><y>0</y><width>893</width><height>629</height></rect></property><property name="windowTitle"><string>Widget</string></property><widget class="QLabel" name="label"><property name="geometry"><rect><x>80</x><y>60</y><width>72</width><height>15</height></rect></property><property name="text"><string>ip</string></property></widget><widget class="QLineEdit" name="ip_edit"><property name="geometry"><rect><x>140</x><y>60</y><width>221</width><height>21</height></rect></property></widget><widget class="QLineEdit" name="port_edit"><property name="geometry"><rect><x>140</x><y>100</y><width>221</width><height>21</height></rect></property></widget><widget class="QLabel" name="label_2"><property name="geometry"><rect><x>80</x><y>100</y><width>72</width><height>15</height></rect></property><property name="text"><string>port</string></property></widget><widget class="QPushButton" name="listen_bt"><property name="geometry"><rect><x>400</x><y>100</y><width>93</width><height>28</height></rect></property><property name="text"><string>listen</string></property></widget><widget class="QTextEdit" name="textEdit"><property name="geometry"><rect><x>60</x><y>190</y><width>761</width><height>401</height></rect></property></widget></widget><layoutdefault spacing="6" margin="11"/><resources/><connections/>
</ui>
测试

相关文章:
通过QT进行服务器和客户端之间的网络通信
客户端 client.pro #------------------------------------------------- # # Project created by QtCreator 2024-07-02T14:11:20 # #-------------------------------------------------QT core gui network #网络通信greaterThan(QT_MAJOR_VERSION, 4): QT widg…...
【STM32 HAL库】DMA+串口
DMA 直接存储器访问 DMA传输,将数据从一个地址空间复制到另一个地址空间。-----“数据搬运工”。 DMA传输无需CPU直接控制传输,也没有中断处理方式那样保留现场和恢复现场,它是通过硬件为RAM和IO设备开辟一条直接传输数据的通道,…...
C#类型基础Part2-对象判等
C#类型基础Part2-对象判等 参考资料引用类型判等简单值类型判等复杂值类型判等 参考资料 《.NET之美-.NET关键技术深入解析》 引用类型判等 先定义两个类型,它们代表直线上的一个点,一个是引用类型class,一个是值类型struct public class…...
13.CSS 打印样式表 悬停下划线动画
CSS 打印样式表 虽然我们不经常从网上实际打印内容,但打印样式表不应被忽视。它们可以用来确保你的网站内容以一种易读和适合打印的方式呈现。这里有一个简单的、独特的打印样式表,你可以用它作为自己的基础: media print {page {size: A4;}body {margin: 0;padding: 0;}body, …...
C#基础:数据库分表的好处和实现方式
一、分表的好处: 1.提升查询速度:分表筛选后再拼接,而不是查大表,速度会显著提升 2.管理容易:根据业务需求,通常会按照时间或者空间来分表 3.提高并发性:降低锁竞争和查询阻塞的风险…...
基于3D开发引擎HOOPS平台的大型三维PLM系统的设计、开发与应用
产品生命周期管理(Product Lifecycle Management,PLM)系统在现代制造业中扮演着至关重要的角色。随着工业4.0和智能制造的推进,PLM系统从最初的CAD和PDM系统发展到现在的全面集成、协作和智能化的平台。本文将探讨基于HOOPS平台的…...
学习React(描述 UI)
React 是一个用于构建用户界面(UI)的 JavaScript 库,用户界面由按钮、文本和图像等小单元内容构建而成。React 帮助你把它们组合成可重用、可嵌套的 组件。从 web 端网站到移动端应用,屏幕上的所有内容都可以被分解成组件。在本章…...
mysql字符类型字段设置默认值为当前时间
-- 2024-07-22 10:22:20 select (DATE_FORMAT(CURRENT_TIMESTAMP, %Y-%m-%d %H:%i:%s)); ALTER TABLE tablename MODIFY COLUNN CREATE_DATE varchar (23) DEFAULT(DATE_FORMAT(CURRENT_TIMESTAMP, %Y-%m-%d %H:%i:%s)) COMMENT "创建日期;...
java题目之数字加密以及如何解密
public class Main6 {public static void main(String[] args) {// 某系统的数字密码(大于0),比如1983,采用加密方式进行传输//定义了一个静态数组int []arr{1,9,8,3};//1.加密//先给每位数加上5for (int i 0; i <arr.length …...
Linux基于CentOS7【yum】【vim】的基础学习,【普通用户提权】
目录 yum生态 什么是yum yum是如何得知目标服务器的地址和下载链接 vim vim模式 命名模式 光标移动 插入模式 i键插 a键插 o键插 底行模式 批量化注释 批量化去注释 创建vim配置文件 例子 高亮功能: 缩进功能: 符号位自动补齐功能…...
盛元广通实验室自动化生物样本库质量控制管理系统
随着我国生物医学研究的不断深入和精准医疗的快速发展,对高质量生物样本的需求日益增长。近年来,我国生物样本库建设取得了显著进展。各级政府、高校和医院纷纷投入资源建设生物样本库,推动了生物样本资源的有效整合和利用。生物样本库的质量…...
Java | 自制AWT单词猜一猜小游戏(测试版)
目录 游戏标题 开发过程 开发想法 技术栈 代码呈现 导包 核心代码 游戏标题 探索知识的迷宫,体验自制AWT单词猜一猜小游戏 在数字时代,学习可以是多彩的,游戏可以是智慧的。我们自豪地推出“单词猜猜猜”是一款结合了教育与娱乐的自制…...
docker搭建ES 8.14 集群
参考:【docker搭建es8集群kibana】_docker 安装生产级 es 8.14 集群-CSDN博客 1、之前已搭建一台单机版的dockerES集群 参见 Elasticsearch docker 安装_docker 安装es8.14.3-CSDN博客 2、现在需要重新搭建为docker ES集群 准备新搭建3个点 一、准备工作 提前开…...
自定义特征的智能演进:Mojo模型中的动态特征选择控制
自定义特征的智能演进:Mojo模型中的动态特征选择控制 在机器学习领域,特征选择是提升模型性能和泛化能力的关键步骤。Mojo模型,作为一种高效的模型部署方式,其对特征的动态选择和控制能力是实现高级机器学习应用的重要特性。本文…...
Git->Git生成patch和使用patch
生成patch git format-patch -1 HEAD -o "输出目录"format-patch:用于生成补丁文件-1:-1 表示最近一次提交,-2 表示生成最近两次提交的补丁。HEAD:HEAD 指向当前分支的最新提交-o:指定生成的补丁文件的输出…...
开发面试算法题求教
在《无尽的拉格朗日》中,有许多不同的星系建筑物。每个星系建筑物的等级不同,带来的影响力也不同。 已知宇宙可以抽象为一个无穷大的平面直角坐标系,现在给定了每个星系建筑物的所在坐标(xi,yi)和它的影响力ri,距离其切比雪夫距离…...
OpenStack中nova的架构
1.1 nova-api 负责接收和相应客户的API调用。 1.2 compute core nova-schedule 负责决定在哪个计算节点运行虚拟机。 nova-compute 通过调用Hypervisor实现虚拟机生命周期的管理。一般运行在计算节点。 hypervisor 对虚拟机进行硬件虚拟化的管理软件ÿ…...
力扣高频SQL 50题(基础版)第五题
文章目录 力扣高频SQL 50题(基础版)第五题1683. 无效的推文题目说明:思路分析:实现过程:结果截图: 力扣高频SQL 50题(基础版)第五题 1683. 无效的推文 题目说明: 表&a…...
Air780EP- AT开发-阿里云应用指南
简介 使用AT方式连接阿里云分为一机一密和一型一密两种方式,其中一机一密又包括HTTP认证二次连接和MQTT直连两种方式 关联文档和使用工具: AT固件获取在线加/解密工具阿里云平台 准备工作 Air780EP_全IO开发板一套,包括天线SIM卡࿰…...
【中项】系统集成项目管理工程师-第4章 信息系统架构-4.4数据架构
前言:系统集成项目管理工程师专业,现分享一些教材知识点。觉得文章还不错的喜欢点赞收藏的同时帮忙点点关注。 软考同样是国家人社部和工信部组织的国家级考试,全称为“全国计算机与软件专业技术资格(水平)考试”&…...
剑指offer20_链表中环的入口节点
链表中环的入口节点 给定一个链表,若其中包含环,则输出环的入口节点。 若其中不包含环,则输出null。 数据范围 节点 val 值取值范围 [ 1 , 1000 ] [1,1000] [1,1000]。 节点 val 值各不相同。 链表长度 [ 0 , 500 ] [0,500] [0,500]。 …...
Java + Spring Boot + Mybatis 实现批量插入
在 Java 中使用 Spring Boot 和 MyBatis 实现批量插入可以通过以下步骤完成。这里提供两种常用方法:使用 MyBatis 的 <foreach> 标签和批处理模式(ExecutorType.BATCH)。 方法一:使用 XML 的 <foreach> 标签ÿ…...
【电力电子】基于STM32F103C8T6单片机双极性SPWM逆变(硬件篇)
本项目是基于 STM32F103C8T6 微控制器的 SPWM(正弦脉宽调制)电源模块,能够生成可调频率和幅值的正弦波交流电源输出。该项目适用于逆变器、UPS电源、变频器等应用场景。 供电电源 输入电压采集 上图为本设计的电源电路,图中 D1 为二极管, 其目的是防止正负极电源反接, …...
WPF八大法则:告别模态窗口卡顿
⚙️ 核心问题:阻塞式模态窗口的缺陷 原始代码中ShowDialog()会阻塞UI线程,导致后续逻辑无法执行: var result modalWindow.ShowDialog(); // 线程阻塞 ProcessResult(result); // 必须等待窗口关闭根本问题:…...
系统掌握PyTorch:图解张量、Autograd、DataLoader、nn.Module与实战模型
本文较长,建议点赞收藏,以免遗失。更多AI大模型应用开发学习视频及资料,尽在聚客AI学院。 本文通过代码驱动的方式,系统讲解PyTorch核心概念和实战技巧,涵盖张量操作、自动微分、数据加载、模型构建和训练全流程&#…...
通过MicroSip配置自己的freeswitch服务器进行调试记录
之前用docker安装的freeswitch的,启动是正常的, 但用下面的Microsip连接不上 主要原因有可能一下几个 1、通过下面命令可以看 [rootlocalhost default]# docker exec -it freeswitch fs_cli -x "sofia status profile internal"Name …...
6️⃣Go 语言中的哈希、加密与序列化:通往区块链世界的钥匙
Go 语言中的哈希、加密与序列化:通往区块链世界的钥匙 一、前言:离区块链还有多远? 区块链听起来可能遥不可及,似乎是只有密码学专家和资深工程师才能涉足的领域。但事实上,构建一个区块链的核心并不复杂,尤其当你已经掌握了一门系统编程语言,比如 Go。 要真正理解区…...
如何在Windows本机安装Python并确保与Python.NET兼容
✅作者简介:2022年博客新星 第八。热爱国学的Java后端开发者,修心和技术同步精进。 🍎个人主页:Java Fans的博客 🍊个人信条:不迁怒,不贰过。小知识,大智慧。 💞当前专栏…...
前端调试HTTP状态码
1xx(信息类状态码) 这类状态码表示临时响应,需要客户端继续处理请求。 100 Continue 服务器已收到请求的初始部分,客户端应继续发送剩余部分。 2xx(成功类状态码) 表示请求已成功被服务器接收、理解并处…...
P10909 [蓝桥杯 2024 国 B] 立定跳远
# P10909 [蓝桥杯 2024 国 B] 立定跳远 ## 题目描述 在运动会上,小明从数轴的原点开始向正方向立定跳远。项目设置了 $n$ 个检查点 $a_1, a_2, \cdots , a_n$ 且 $a_i \ge a_{i−1} > 0$。小明必须先后跳跃到每个检查点上且只能跳跃到检查点上。同时࿰…...
