利用 QTcpSocket 实现的进程间通信
简介
做一个简答的进程间通信的原型,主要是为了了解进程间通信的一些原理
本文是利用 QTcpSocket 来实现的。
主要步骤
实现之后的UI界面如下,主要步骤有一下几步:
1、ServerSocket 点击建立连接(此时 ServerSocket 开始监听端口为 5555 的其他程序)
2、WorkerSocket 点击连接服务器(通过制定的IP地址和端口主动连接服务器)
3、连接之后可以开始互相发送消息。
代码实现
列出了关键的几个文件
// ServerSocket.h
#pragma once#include <QtWidgets/QMainWindow>
#include "ui_ServerSocket.h"
#include <QtNetwork/QTcpServer>class ServerSocket : public QMainWindow
{Q_OBJECTpublic:ServerSocket(QWidget *parent = Q_NULLPTR);private slots:void OnBtnInitSocket(); // 开始监听workervoid OnBtnSendClick();void ServerReadData();void ServerNewConnection(); // 和work端建立连接时void ServerDisConnection(); // 和work端断开连接时private:Ui::ServerSocketClass ui;QTcpServer *m_TCPServer;QTcpSocket *m_TCPSocket;
};
// ServerSocket.cpp
#include "ServerSocket.h"
#include <QtWidgets/QMessageBox>
#include <QtNetwork/QTcpSocket>struct DataHeader
{char magic;int length;int intlength;
};ServerSocket::ServerSocket(QWidget *parent): QMainWindow(parent), m_TCPServer(nullptr), m_TCPSocket(nullptr)
{ui.setupUi(this);ui.lineEdit_port->setText("5550");connect(ui.btn_initPort, SIGNAL(clicked()), this, SLOT(OnBtnInitSocket()));connect(ui.btn_send, SIGNAL(clicked()), this, SLOT(OnBtnSendClick()));
}void ServerSocket::OnBtnInitSocket()
{m_TCPServer = new QTcpServer();int port = ui.lineEdit_port->text().toInt();if (!m_TCPServer->listen(QHostAddress::Any, port)) // 监听信息(监听的机器的IP地址和端口){QMessageBox::information(this, "QT TPC", "listen falure !");return;}else{QMessageBox::information(this, "QT TPC", "listen succeed !");}// 当监听到信号的时候会发出newConnection() 信号connect(m_TCPServer, SIGNAL(newConnection()), this, SLOT(ServerNewConnection()));
}void ServerSocket::ServerNewConnection()
{m_TCPSocket = m_TCPServer->nextPendingConnection();if (!m_TCPSocket){QMessageBox::information(this, "QT TPC", "connect falure !");return;}else{QMessageBox::information(this, "QT TPC", "connect succeed");connect(m_TCPSocket, SIGNAL(readyRead()), this, SLOT(ServerReadData()));connect(m_TCPSocket, SIGNAL(disconnected()), this, SLOT(ServerDisConnection()));}
}void ServerSocket::ServerReadData()
{QByteArray resArray = m_TCPSocket->read(1024);char* pCharRes;QDataStream stream(&resArray, QIODevice::ReadOnly);stream >> pCharRes;if (strlen(pCharRes/*buffer*/) > 0){QString showNsg = pCharRes/*buffer*/;ui.textBrowser_receive->append(showNsg);}else{QMessageBox::information(this, "QT TCP", "Data error");return;}
}void ServerSocket::ServerDisConnection()
{QMessageBox::information(this, "QT TCP", "Disconnect from the client");return;
}void ServerSocket::OnBtnSendClick()
{char sendMsgChar[1024] = { 0 };QString sendMsg = ui.textEdit_send->toPlainText();if (sendMsg.isEmpty()){QMessageBox::information(this, "QT TCP", "Data is empty, please enter data");return;}QByteArray block;QDataStream stream(&block, QIODevice::WriteOnly);stream.setVersion(QDataStream::Qt_5_5);stream << sendMsg.toStdString().c_str();if (m_TCPSocket->isValid()){int sendRe = m_TCPSocket->write(block);if (-1 == sendRe){QMessageBox::information(this, "QT TCP", "Failed to send data");}}else{QMessageBox::information(this, "QT TCP", "Invalid socket");}
}
// WorkerSocket.h
#pragma once
#include <QtWidgets/QMainWindow>
#include "ui_WorkerSocket.h"
#include <QtNetwork/QTcpSocket>class WorkerSocket : public QMainWindow
{Q_OBJECTpublic:WorkerSocket(QWidget *parent = Q_NULLPTR);void JumpToServer();private slots:void OnConnectBtnClicked(); // 点击连接的按钮,开始连接服务器void OnSendBtnClicked(); // 点击发送按钮,发送消息void WorkerReceiveData(); // 接收到消息,解析数据private:Ui::WorkerSocketClass* ui;QTcpSocket *m_clientSocket;
};
// WorkerSocket.cpp
#include "WorkerSocket.h"
#include <QtWidgets/QMessageBox>
#include <QProcess>
#include <QDebug>
#include <QTextBrowser>WorkerSocket::WorkerSocket(QWidget *parent): QMainWindow(parent),ui(new Ui::WorkerSocketClass()) // 成员指针在使用之前需要先初始化
{ui->setupUi(this);ui->lineEdit_IP->setText("10.4.38.33"); // 输入服务端机器的IP地址ui->lineEdit_port->setText("5555"); // 保证服务端和工作端的端口一致即可connect(ui->btn_connect, SIGNAL(clicked()), this, SLOT(OnConnectBtnClicked()));connect(ui->btn_send, SIGNAL(clicked()), this, SLOT(OnSendBtnClicked()));
}// 与服务器建立连接后
void WorkerSocket::OnConnectBtnClicked()
{m_clientSocket = new QTcpSocket();QString ip = ui->lineEdit_IP->text();int port = ui->lineEdit_port->text().toInt();m_clientSocket->connectToHost(ip, port);if (!m_clientSocket->waitForConnected(10000)){QMessageBox::information(this, "QT TCP", "connect failure!");return;}QMessageBox::information(this, "QT TCP", "connect succeed!");connect(m_clientSocket, SIGNAL(readyRead()), this, SLOT(WorkerReceiveData()));
}// 发送消息
void WorkerSocket::OnSendBtnClicked()
{QString sendMsg = ui->textEdit_send->toPlainText();QByteArray resArray;QDataStream stream(&resArray, QIODevice::WriteOnly);stream << sendMsg.toStdString().c_str();qint64 sendRes = m_clientSocket->write(resArray);
}// 接受到服务端传过来的数据
void WorkerSocket::WorkerReceiveData()
{QByteArray resArray = m_clientSocket->readAll();QDataStream stream(&resArray, QIODevice::ReadOnly);char* pCharRes;stream >> pCharRes;if (strlen(pCharRes/*buffer*/) > 0){QString showNsg = pCharRes/*buffer*/;ui->textBrowser_receive->append(showNsg);}else{QMessageBox::information(this, "QT TCP", "Data error");return;}
}
利用 QTcpSocket 实现的进程间通信相关推荐
- java 内存映射文件进程间通讯_[转]Windows环境下利用“共享内存”实现进程间通信的C/C++代码---利用CreateFileMapping和MapViewOfFile...
进程间的通信方式有很多种, 上次我们说了最傻瓜的"共享外存/文件"的方法. 那么, 在本文中, 我们即将学习"共享内存"的方式实现进程间的通信, 这是IPC最快 ...
- 利用dpdk rte_ring实现进程间通信
进程间通信有很多方式,如果两个进程是在同一台机器上运行的,效率比较高的通信方式就是共享内存.关于共享内存的实现方式,双方可以通过mmap方式去映射到相同的内存上进而实现内存共享. DPDK实现的rin ...
- Unix网络编程--进程间通信--管道通信
所有式样的Unix都提供管道,它由 pipe 函数创建,提供一个单路(单向)数据流. 原型如下: #include <unistd.h> int pipe(int ...
- 嵌入式系统中进程间通信的监视方法
概述 复杂的嵌入式系统中,常常同时运行着相当多的进程.这些进程之间频繁的进行着大量的通信动作.进程的运行状态与这些不断发生的通信有着直接和紧密的联系.通过对进程间通信的监视,开发人员可以掌控系统内部运 ...
- NIO详解(七):进程间通信(MappedByteBuffer)
1. 前言 最近在研究Java进程间通信,为了了解Java中的SharedMemory共享内存.我特地去研究了一些Java NIO进程间通信的方式. 2. Java NIO MappedByteBuf ...
- 【操作系统】进程间通信的五种方式
引言 1.进程对白:管道.记名管道.套接字 1.管道 2.虫洞:套接字 3.信号 4.信号旗语:信号量 5.进程拥抱:共享内存 引言 进程作为人类的发明,自然免不了脱离人类的习性,也有通信需求.如果进 ...
- Qt QTcpSocket 对连接服务器中断的不同情况进行判定
简述 对于一个C/S结构的程序,客户端有些时候需要实时得知与服务器的连接状态.而对于客户端与服务器断开连接的因素很多,现在就目前遇到的情况进行一下总结. 分为下面六种不同情况 客户端网线断开 客户端网 ...
- linux进程间通信(IPC) ---无名管道
管道概述 管道(pipe)又称无名管道 无名管道是一种特殊类型的文件,在应用层体现为两个打开的文件描述符 任何一个进程在创建的时候,系统都会,给它分配4G的虚拟内存,分为3G的用户空间和1G的内核空间 ...
- Linux应用开发【第四章】Linux进程间通信应用开发
文章目录 4 Linux进程间通信应用开发 4.1 初识进程 4.1.1 进程的概念 4.1.1.1 程序 4.1.1.2 进程 4.1.1.3 进程和程序的联系 4.1.1.4 进程和程序的区别 4 ...
- 分布式环境下,互斥性与幂等性问题,分析与解决思路
欢迎关注方志朋的博客,回复"666"获面试宝典 随着互联网信息技术的飞速发展,数据量不断增大,业务逻辑也日趋复杂,对系统的高并发访问.海量数据处理的场景也越来越多.如何用较低成本实 ...
最新文章
- 在Xen虚拟机下修改或同步时间失败的解决方法
- Visual Studio常用快捷键(非常实用)
- 保存/恢复cxGrid布局
- 机器学习必学10大算法
- JAVA基础知识系列---进程、线程安全
- java 常量变量使用_java常量和变量入门教程
- 计算机辅助普通话水平测试指导,计算机辅助普通话水平测试指南38563
- embedding lookup
- 谷粒学院项目总结(持续更新)
- 计算机二级数据库题库百度云,计算机二级数据库试题及答案
- UE4针对特殊的透明物体不应用后期效果
- 怎样理解OOP?OOP又是什么?
- Luminar 4:AI 人像照片增强器
- 虚拟服务器和vdi,比较瘦客户端和VDI
- python控制手机
- 好好吃饭,才是最大的教养
- Google Android 原生Rom 下载地址及刷机教程--Factory Images for Nexus and Pixel Devices
- 浅谈人工智能:现状、任务、构架与统一
- 基于 PIR 的运动检测:传感器解决方案
- ibatis mysql存储过程_分步详解 如何在iBatis中调用存储过程