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

QT+多线程TCP服务器+进阶版

        针对之前的服务器,如果子线程工作类里面需要使用socket发送消息,必须要使用信号与槽的方法, 先发送一个信号给父进程,父进程调用socket发送消息(原因是QT防止父子进程抢夺同一资源,因此直接规定父子进程不能使用同一资源,可能很片面,但至少针对socket这个类是这样的),因此,为了更好的使用多线程TCP服务器,下面介绍一种新的方法。

1、新建一个编译无错误的工程

2、在pro文件中加入network

3、新建两个类,一个Worker类继承QObject,一个TcpServer类继承QTcpServer

4、编辑服务器界面

5、给控件命名

6、查找本地有效的IPV4,并用combox控件显示

    QList<QHostAddress> ipAddressesList = QNetworkInterface::allAddresses();for (int i = 0; i < ipAddressesList.size(); ++i) {if (!ipAddressesList.at(i).isNull()//IP地址是否为NULL&& ipAddressesList.at(i).toIPv4Address() != 0//是否是IPV4地址){ui->IPComboBox->addItem(ipAddressesList.at(i).toString());}}

7、创建Server对象,绑定连接服务器按钮和创建代码

#include "tcpserver.h"
TcpServer *tcpserver = NULL;//TcpServer这个是自定义的服务器类void Widget::on_connectPushButton_clicked()
{if(ui->connectPushButton->text().contains("打开服务器")){tcpserver = new TcpServer();           //实例化tcpserver对象tcpserver->listen( QHostAddress(ui->IPComboBox->currentText()),ui->portLineEdit->text().toInt());//进行IP地址与端口的监听ui->connectPushButton->setText("断开服务器");}else{tcpserver->close();ui->connectPushButton->setText("打开服务器");}
}

8、当客户端被连接时,TcpServer类会自己调用incomingConnection方法,然后我们需要重写这个方法,首先就是新建一个工作类,然后把套接字文件符传送过去,然后在构造函数初始化套接字

protected:void incomingConnection(qintptr socketDescriptor) override; //当客户端连接时被调用。
void TcpServer::incomingConnection(qintptr socketDescriptor)
{QThread *thread = new QThread();Worker *worker = new Worker(socketDescriptor);//socketDescriptor这个参数时套接字的描述符,用于生成套接字socketconnect(thread, &QThread::finished, thread, &QThread::deleteLater); //释放线程资源worker->moveToThread(thread);thread->start();
}

 9、先修改工作类worker的构造函数,将套接字描述符加入

public:explicit Worker(qintptr socketDescriptor,QObject *parent = nullptr);Worker::Worker(qintptr socketDescriptor, QObject *parent): QObject{parent}
{m_socketDescriptor=socketDescriptor;m_tcpsocket = new QTcpSocket(this);m_tcpsocket->setSocketDescriptor(m_socketDescriptor);
}

10、获取套接字之后开始处理读到的数据,在工作类中建立读信号和槽函数关系

public slots:void onReadyRead();connect(m_tcpsocket,&QTcpSocket::readyRead,this,&Worker::onReadyRead);void Worker::onReadyRead()
{QByteArray data = m_tcpsocket->readAll();m_tcpsocket->write("receive : "+data);
}

12、编译通过,且连接成功,可以将收到的消息发给服务器

 13、开始处理发送信息的消息,首先Widget界面有一个发送按钮,用于发送数据给客户端,代码实际操作时发送信号给工作类处理

signals:void sendDataSignals(QString data);void Widget::on_sendPushButton_clicked()
{emit sendDataSignals(ui->sendPlainTextEdit->toPlainText());
}

我们如何让Widget和worker工作类产生联系,利用中间类TcpServer,我们先将sendDataSignals信号发送到TcpServer类中,利用connect信号转信号,然后等待TcpServer发送 sendDataSignals信号时绑定Worker类的槽函数进行发送数据

connect(this,&Widget::sendDataSignals,tcpserver,&TcpServer::sendDataSignals);
connect(this,&TcpServer::sendDataSignals,worker,&Worker::sendData_slots);
void Worker::sendData_slots(QString data)
{m_tcpsocket->write("send : "+data.toUtf8()+"\r\n");
}

 14、编译代码,运行成功,可以成功收发数据

15、当接收到数据后我们让其在网络数据接收窗口显示,采用信号与槽的机制

void Worker::onReadyRead()
{QByteArray data = m_tcpsocket->readAll();m_tcpsocket->write("i am server,receive : "+data+"\r\n");emit readDisplaySignals(QString::fromUtf8(data));
}
connect(worker,&Worker::readDisplaySignals,this,&TcpServer::readDisplaySignals);
connect(tcpserver,&TcpServer::readDisplaySignals,this,&Widget::readDataDisplay_slots);
void Widget::readDataDisplay_slots(QString data)
{QString str=ui->receivePlainTextEdit->toPlainText();//接收区之前的内容QDateTime nowtime = QDateTime::currentDateTime();str += "[" + nowtime.toString("yyyy-MM-dd hh:mm:ss") + "] "+ "RX: ";//记录当前时间str = str + data + "\r\n";//当前接收最新消息ui->receivePlainTextEdit->setPlainText(str);
}

16、测试成功

17、完整工程代码

链接:https://pan.baidu.com/s/1wqfFoLKSrARjDHIX0Y-diQ?
提取码:生日

相关文章:

QT+多线程TCP服务器+进阶版

针对之前的服务器&#xff0c;如果子线程工作类里面需要使用socket发送消息&#xff0c;必须要使用信号与槽的方法&#xff0c; 先发送一个信号给父进程&#xff0c;父进程调用socket发送消息&#xff08;原因是QT防止父子进程抢夺同一资源&#xff0c;因此直接规定父子进程不能…...

Java入门基础学习笔记12——变量详解

变量详解&#xff1a; 变量里的数据在计算机中的存储原理。 二进制&#xff1a; 只有0和1&#xff0c; 按照逢2进1的方式表示数据。 十进制转二进制的算法&#xff1a; 除二取余法。 6是110 13是1101 计算机中表示数据的最小单元&#xff1a;一个字节&#xff08;byte&…...

bitmap requires a valid src attribute

关于作者&#xff1a;CSDN内容合伙人、技术专家&#xff0c; 从零开始做日活千万级APP。 专注于分享各领域原创系列文章 &#xff0c;擅长java后端、移动开发、商业变现、人工智能等&#xff0c;希望大家多多支持。 未经允许不得转载 目录 一、导读二、概览三、问题记录四、 推…...

Java刷题-基础篇

目录 题目1&#xff1a;打印1~100内奇数和、偶数和 题目2&#xff1a;计算5的阶乘 题目3&#xff1a;计算 1!2!3!4!5! 的和 题目4&#xff1a;找1~100之间即能被3整除&#xff0c;又能被5整除的数字&#xff0c;要求必须使用break/continue 题目5&#xff1a;实现猜数字小…...

Linux——mysql运维篇

回顾基本语句&#xff1a; 数据定义语言 ( DDL ) 。这类语言用于定义和修改数据库的结构&#xff0c;包括创建、删除和修改数据库、表、视图和索引等对象。主要的语句关键字包括 CREATE 、 DROP 、 ALTER 、 RENAME 、 TRUNCATE 等。 create database 数据库 &…...

力扣每日一题-统计已测试设备-2024.5.10

力扣题目&#xff1a;统计已测试设备 题目链接: 2960.统计已测试设备 题目描述 代码思路 根据题目内容&#xff0c;第一感是根据题目模拟整个过程&#xff0c;在每一步中修改所有设备的电量百分比。但稍加思索&#xff0c;发现可以利用已测试设备的数量作为需要减少的设备电…...

代码+视频,R言语处理数据中的缺失值

在SCI论文中&#xff0c;我们不可避免和缺失数据打交道&#xff0c;特别是在回顾性研究&#xff0c;对于缺失的协变量&#xff08;就是混杂因素&#xff09;&#xff0c;我们可以使用插补补齐数据&#xff0c;但是对于结局变量和原因变量的缺失&#xff0c;我们不能这么做。部分…...

PGSync安装使用教程(PostgreSQL数据实时同步至Elasticsearch)

说明 pgsync项目有两个&#xff0c;一个是ankane/pgsync&#xff0c;用于pgsql之间的数据同步&#xff0c;另一个是toluaina/pgsync&#xff0c;用于pgsql的数据同步至es&#xff0c;本教程适用于第二个项目。 pgsync应该是目前为止唯二支持es8的数据同步工具&#xff0c;另一…...

前端主题切换的多种方式

动态link标签加载不同主题css **原理&#xff1a;**提前准备好几套CSS主题样式文件&#xff0c;在点击切换主题时&#xff0c;创建link标签动态加载到head标签中&#xff0c;或者是动态改变link标签的href属性。 缺点&#xff1a; 动态加载样式文件&#xff0c;如果文件过大网…...

使用RESTful API构建 web 应用程序

RESTful API是一种基于HTTP协议的架构风格&#xff0c;用于设计网络应用程序的 API。它强调使用标准的HTTP方法&#xff08;如GET、POST、PUT和DELETE&#xff09;对资源进行操作&#xff0c;并使用统一的资源标识符&#xff08;URI&#xff09;来唯一标识每个资源。RESTful AP…...

KaiOS Data PDN 数据建立流程

代码逻辑 APN创建 在 DataCallManager.jsm中,会对所有apnsetting创建一个datacall,其中会包含dataprofile的成员(通过apn参数来创建),在之后的流程用于直接发送到modem建立PDN。 PDN建立 1、DataCallManager.jsm -dcInterface.setupDataCall //RILNetworkInterface.c…...

Mybatis-Plus常用的增删改查坑

添加依赖 <!--实体类上加上Data注解就不用写get&#xff0c;set&#xff0c;toString&#xff0c;equals等方法了--><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><optional>true</optional…...

初识指针(4)<C语言>

前言 前面的文章&#xff0c;已经对指针的基础概念以及运用有了初步了解&#xff0c;我们可以进一步探究指针比较深入的知识&#xff0c;下文将主要介绍&#xff1a;使用指针数组模拟二维数组、字符指针变量、数组指针、二维数组传参的本质、函数指针、typedef关键字等。 目录…...

pyqt 工具栏QToolBar控件

pyqt 工具栏QToolBar控件 QToolBar控件介绍效果代码 QToolBar控件介绍 QToolBar 是 PyQt&#xff08;中的一个控件&#xff0c;它提供了一个工具栏&#xff0c;通常包含一系列的工具按钮或下拉菜单&#xff0c;用于提供对应用程序功能的快速访问。 QToolBar 通常与 QMainWind…...

SystemVerilog/Verilog中的仿真延时建模之模块路径延时

一 概要 模块路径延迟,描述的是模块中信号从源端到目的端传输的延迟。 路径以及对应的延迟是在模块中的specify块中指定的,其中信号源端一般为input或者inout,而目的端则只能为output或者inout.在specify中指定的模块路径,常见的形式主要三种,分别是: 简单路径(Simple Path…...

代码随想录算法训练营Day36 | 738.单调递增的数字、968.监控二叉树、贪心算法总结 | Python | 个人记录向

本文目录 738.单调递增的数字做题看文章 968.监控二叉树做题看文章 贪心算法总结以往忽略的知识点小结个人体会 738.单调递增的数字 代码随想录&#xff1a;738.单调递增的数字 Leetcode&#xff1a;738.单调递增的数字 做题 无思路。 看文章 例如&#xff1a;98&#xff…...

FME学习之旅---day26

我们付出一些成本&#xff0c;时间的或者其他&#xff0c;最终总能收获一些什么。 【由于上周&#xff0c;上班状态不是很好&#xff0c;事情多又杂&#xff0c;没有学习的劲头&#xff0c;就短暂的休息了一下下。双休爬山&#xff0c;给自己上了强度&#xff0c;今天才缓过来…...

JAVA学习-练习试用Java实现电话号码的字母组合

问题: 给定一个仅包含数字 2-9 的字符串&#xff0c;返回所有它能表示的字母组合。答案可以按 任意顺序 返回。 给出数字到字母的映射如下&#xff08;与电话按键相同&#xff09;。注意 1 不对应任何字母。 示例 1&#xff1a; 输入&#xff1a;digits "23" 输…...

js代码中关于async await的滥用 async await的滥用

概念&#xff1a; 返回值&#xff1a; async返回一个promise---这个返回值是默认自发行为 async function name1(params) {console.log(params) } let result name1(lion) console.log(result) // Promise { undefined } result.then(res > console.log(res)) // undefin…...

基础算法,贪心算法,贪心策略,OJ练习

文章目录 一、概念二、OJ练习2.1 区间选点2.2 区间合并2.3 区间2.4 合并果子2.5 排队接水2.6 货仓选址2.7 防晒2.8 畜栏预定2.9 雷达设备2.10 国王游戏2.11 耍杂技的牛2.12 给树染色2.13 任务2.14 能量石 三、总结 一、概念 贪心是一种在每次决策时采取当前意义下最优策略的算…...

保姆级教程:用VMware和Kali复现Vulnstack红日靶场2的完整渗透流程(附CS联动技巧)

红队实战进阶&#xff1a;Kali与Cobalt Strike协同渗透Vulnstack靶场全解析 环境配置与网络拓扑设计 在开始渗透测试之前&#xff0c;正确的环境搭建是成功的基础。不同于简单的虚拟机启动&#xff0c;专业级红队演练需要精确模拟企业内网环境。我们采用三台靶机&#xff08;WE…...

DNS区域传送漏洞详解:从原理到防御(以Bind9为例)

DNS区域传送漏洞深度解析与BIND9安全加固实战指南 当你在浏览器输入一个网址时&#xff0c;背后发生的DNS查询过程就像一场精密的交响乐演出。而区域传送&#xff08;Zone Transfer&#xff09;作为DNS系统中的关键机制&#xff0c;本应是乐谱中协调各声部的指挥棒&#xff0c…...

如何从WiringPi旧版本升级到3.18新架构:完整迁移指南

如何从WiringPi旧版本升级到3.18新架构&#xff1a;完整迁移指南 【免费下载链接】WiringPi Gordons Arduino wiring-like WiringPi Library for the Raspberry Pi (Unofficial Mirror for WiringPi bindings) 项目地址: https://gitcode.com/gh_mirrors/wi/WiringPi Wi…...

从零搭建Binance Trade Bot:精通加密货币自动交易工具配置与使用

从零搭建Binance Trade Bot&#xff1a;精通加密货币自动交易工具配置与使用 【免费下载链接】binance-trade-bot Automated cryptocurrency trading bot 项目地址: https://gitcode.com/gh_mirrors/bi/binance-trade-bot 一、核心功能解析&#xff1a;Binance Trade Bo…...

华硕笔记本终极性能调校指南:GHelper开源控制工具完全解析

华硕笔记本终极性能调校指南&#xff1a;GHelper开源控制工具完全解析 【免费下载链接】g-helper Lightweight Armoury Crate alternative for Asus laptops. Control tool for ROG Zephyrus G14, G15, G16, M16, Flow X13, Flow X16, TUF, Strix, Scar and other models 项目…...

ChatTTS社区生态:GitHub项目活跃度与更新频率观察

ChatTTS社区生态&#xff1a;GitHub项目活跃度与更新频率观察 1. 项目概述与核心价值 ChatTTS作为目前开源语音合成领域的明星项目&#xff0c;以其卓越的拟真度和自然度赢得了广泛关注。这个专门针对中文对话优化的语音合成模型&#xff0c;能够自动生成极其自然的停顿、换气…...

为什么你的单细胞数据需要sctransform?Seurat标准化方法对比

为什么你的单细胞数据需要sctransform&#xff1f;深度解析标准化方法的技术革命 单细胞RNA测序技术正在重塑我们对生命复杂性的理解。当研究人员第一次看到单细胞数据中那些令人眼花缭乱的基因表达矩阵时&#xff0c;往往会面临一个关键问题&#xff1a;如何从这些充满技术噪音…...

文墨共鸣大模型安装包依赖分析与环境冲突解决

文墨共鸣大模型安装包依赖分析与环境冲突解决 你是不是也遇到过这种情况&#xff1a;拿到一个项目&#xff0c;兴冲冲地运行 pip install -r requirements.txt&#xff0c;结果屏幕上开始疯狂报错&#xff0c;各种版本不兼容、找不到模块、编译失败的信息轮番轰炸。折腾了几个…...

书匠策AI:解锁毕业论文写作新姿势,你的学术“超级大脑”已上线!

毕业季的钟声敲响&#xff0c;论文写作的“战役”也随之打响。面对堆积如山的文献、错综复杂的逻辑框架&#xff0c;以及那令人抓狂的格式要求&#xff0c;你是不是也感到力不从心&#xff0c;甚至开始怀疑人生&#xff1f;别怕&#xff0c;今天咱们就来认识一位学术界的“超级…...

3大维度重构投资决策:用TradingAgents-CN打造智能交易系统

3大维度重构投资决策&#xff1a;用TradingAgents-CN打造智能交易系统 【免费下载链接】TradingAgents-CN 基于多智能体LLM的中文金融交易框架 - TradingAgents中文增强版 项目地址: https://gitcode.com/GitHub_Trending/tr/TradingAgents-CN 在数字化投资时代&#xf…...