python socket编程6 - 使用PyQt6 开发UI界面实现TCP server和TCP client单机通讯的例子

使用PyQt6 开发UI界面实现TCP server和TCP client单机通讯的示例。

一、PyQt6 实现的界面

在这里插入图片描述

二、TCP server代码的修改示意

在这里插入图片描述

界面提供网络参数的配置,以及提供人机交互过程中的数据获取和显示。

1、把上面的server代码封装成两个部分

A、class Server 负责接受UI界面的参数并通过信号与后台线程通讯
B、class ServerSocketReceiveThread 封装了 server socket 接收数据的行为并提供信号与Server交换数据

如果在UI界面调用while语句接收socket数据,会导致界面卡死。
所以使用新线程运行socket接收数据的操作,通过信号传递给Server中定义的方法,实现数据传递。

下图是原来的代码与修改后的代码部分映射的关系:
在这里插入图片描述

2、Server的完整代码

class Server:

    def __init__(self, ui, server_ip, server_hostname, server_port):

        self.ui = ui  # 主界面
        self.ip = server_ip  # 服务器ip地址
        self.port = server_port  # 服务器端口号
        self.serverName = server_hostname  # 显示名称
        self.is_running = False  # 是否已经启动

        self.socket = None  # socket
        self.socketThread = None  # 新的 socket receive 线程

        self.start()

    def start(self):
        if not self.is_running:
            self.is_running = True
            self.socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
            self.socket.bind((self.ip, self.port))  # 绑定IP与端口
            self.socket.listen(1)  # 设定最大连接数
            self.startSocketReceiveThread()

    def stop(self):
        try:
            if self.is_running:
                self.is_running = False
                if self.socketThread.is_running:
                    self.socketThread.stop()
        except Exception as e:
            print(e)

    def startSocketReceiveThread(self):
        self.socketThread = ServerSocketReceiveThread(self.socket)
        self.socketThread.clientConnection.connect(self.socket_client_connect_trigger)
        self.socketThread.receivedClientData.connect(self.show_client_message)
        self.socketThread.serverStatus.connect(self.server_status_trigger)
        self.socketThread.start()

    def server_status_trigger(self, status):
        self.ui.statusbar.showMessage(status)

    def socket_client_connect_trigger(self, state):
        if state == 'connect':
            self.ui.statusbar.showMessage("客户端已经连接。")
        else:
            self.ui.statusbar.showMessage("客户端已经断开。")

    def show_client_message(self, message):
        self.ui.textEdit.append('客户端:' + message)

    def send_message_to_client(self, message):
        if self.is_running:
            self.ui.textEdit.append(self.serverName + ':' + message)
            self.socketThread.send_data_to_client(message)
3、ServerSocketReceiveThread 完整代码

class ServerSocketReceiveThread(QThread):
    clientConnection: pyqtSignal = pyqtSignal(str)  # 向主线程发送连接状态标志
    receivedClientData: pyqtSignal = pyqtSignal(str)  # 向主线程发送接受到客户端的数据
    serverStatus: pyqtSignal = pyqtSignal(str)  # 向主线程发送服务器状态

    def __init__(self, serverSocket):
        super(ServerSocketReceiveThread, self).__init__()
        self.serverSocket = serverSocket
        self.clientSocket = None
        self.addr = None
        self.is_running = True

    def run(self):
        self.serverStatus.emit("服务已经启动,等待客户端的连接......")
        self.clientSocket, self.addr = self.serverSocket.accept()  # 接受客户端的连接
        self.emitConnectEvent('connect')  # 发送通知到主界面
        self.startReceiveData()

    def startReceiveData(self):
        while self.is_running:
            try:
                data = self.clientSocket.recv(1024).decode('utf-8')  
                if not data:
                    self.emitConnectEvent('disconnect')  # 发送通知到主界面
                    break
                self.sendClientDataToUi(data)
            except ConnectionResetError as reason:
                self.sendClientDataToUi("已经离开对话。")
                self.is_running = False
                self.emitConnectEvent('disconnect')  # 发送通知到主界面
                break
        self.clientSocket.close()
        self.serverSocket.close()
        self.serverStatus.emit("服务已经关闭。")

    def send_data_to_client(self, message):
        try:
            self.clientSocket.send(message.encode("utf-8"))
        except Exception as reason:
            print("发送失败,原因 = ", reason)

    def stop(self):
        if self.is_running:
            self.is_running = False

    def emitConnectEvent(self, state):
        self.clientConnection.emit(state)

    def sendClientDataToUi(self, message):
        self.receivedClientData.emit(message)

三、TCP Client 代码也是同样封装为两部分

1、class Client完整代码

class Client:

    def __init__(self, ui, ip, clientName, port):
        self.ui = ui
        self.ip = ip
        self.hostName = clientName
        self.port = port

        self.socket = None
        self.socketThread = None
        self.connect_server()

    def connect_server(self):
        self.socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        self.socketThread = ClientSocketReceiveThread(self.socket)
        self.socketThread.receivedServerData.connect(self.update_ui_chat_content)
        if self.connect_success(self.ip, self.port):
            self.socketThread.start()

    def update_ui_chat_content(self, serverMessage):
        self.ui.textEdit_2.append("服务端:" + serverMessage)

    def stop(self):
        self.socketThread.stop()

    def send_data(self, sentence):
        self.ui.textEdit_2.append(self.hostName + ":" + sentence)
        self.socket.send(sentence.encode())

    def connect_success(self, ip, port):
        try:
            self.socket.connect((ip, port))
            return True
        except Exception as reason:
            print(reason)
            return False
2、class ClientSocketReceiveThread完整代码

class ClientSocketReceiveThread(QThread):
    receivedServerData: pyqtSignal = pyqtSignal(str)  # 向主线程发送接受到客户端的数据

    def __init__(self, clientSocket):
        super(ClientSocketReceiveThread, self).__init__()
        self.clientSocket = clientSocket
        self.is_running = True

    def stop(self):
        self.is_running = False
        self.clientSocket.close()

    def run(self):
        while self.is_running:
            try:
                msg = self.clientSocket.recv(1024).decode("utf-8")  # 接受服务端消息
                if not msg:
                    break
                self.receivedServerData.emit(msg)
            except Exception as reason:
                print(reason)
                break
        self.stop()
        self.receivedServerData.emit("已经与服务端断开。")

四、ui_Main.py代码



class Ui_MainWindow(object):
    def setupUi(self, MainWindow):
        MainWindow.setObjectName("MainWindow")
        MainWindow.resize(957, 600)
        self.centralwidget = QtWidgets.QWidget(parent=MainWindow)
        self.centralwidget.setObjectName("centralwidget")
        self.verticalLayout = QtWidgets.QVBoxLayout(self.centralwidget)
        self.verticalLayout.setObjectName("verticalLayout")
        self.tabWidget = QtWidgets.QTabWidget(parent=self.centralwidget)
        self.tabWidget.setObjectName("tabWidget")
        self.tab = QtWidgets.QWidget()
        self.tab.setObjectName("tab")
        self.horizontalLayout_10 = QtWidgets.QHBoxLayout(self.tab)
        self.horizontalLayout_10.setObjectName("horizontalLayout_10")
        self.verticalLayout_5 = QtWidgets.QVBoxLayout()
        self.verticalLayout_5.setObjectName("verticalLayout_5")
        self.groupBox = QtWidgets.QGroupBox(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.groupBox.setFont(font)
        self.groupBox.setObjectName("groupBox")
        self.verticalLayout_2 = QtWidgets.QVBoxLayout(self.groupBox)
        self.verticalLayout_2.setObjectName("verticalLayout_2")
        self.horizontalLayout_2 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_2.setObjectName("horizontalLayout_2")
        self.label = QtWidgets.QLabel(parent=self.groupBox)
        self.label.setObjectName("label")
        self.horizontalLayout_2.addWidget(self.label)
        self.lineEdit = QtWidgets.QLineEdit(parent=self.groupBox)
        self.lineEdit.setObjectName("lineEdit")
        self.horizontalLayout_2.addWidget(self.lineEdit)
        self.pushButton_3 = QtWidgets.QPushButton(parent=self.groupBox)
        self.pushButton_3.setObjectName("pushButton_3")
        self.horizontalLayout_2.addWidget(self.pushButton_3)
        self.verticalLayout_2.addLayout(self.horizontalLayout_2)
        self.horizontalLayout_3 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_3.setObjectName("horizontalLayout_3")
        self.label_2 = QtWidgets.QLabel(parent=self.groupBox)
        self.label_2.setObjectName("label_2")
        self.horizontalLayout_3.addWidget(self.label_2)
        self.lineEdit_2 = QtWidgets.QLineEdit(parent=self.groupBox)
        self.lineEdit_2.setObjectName("lineEdit_2")
        self.horizontalLayout_3.addWidget(self.lineEdit_2)
        spacerItem = QtWidgets.QSpacerItem(40, 20, QtWidgets.QSizePolicy.Policy.Expanding, QtWidgets.QSizePolicy.Policy.Minimum)
        self.horizontalLayout_3.addItem(spacerItem)
        self.horizontalLayout_3.setStretch(2, 1)
        self.verticalLayout_2.addLayout(self.horizontalLayout_3)
        self.horizontalLayout_4 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_4.setObjectName("horizontalLayout_4")
        self.verticalLayout_2.addLayout(self.horizontalLayout_4)
        self.verticalLayout_5.addWidget(self.groupBox)
        self.verticalLayout_4 = QtWidgets.QVBoxLayout()
        self.verticalLayout_4.setObjectName("verticalLayout_4")
        self.horizontalLayout = QtWidgets.QHBoxLayout()
        self.horizontalLayout.setObjectName("horizontalLayout")
        spacerItem1 = QtWidgets.QSpacerItem(40, 20, QtWidgets.QSizePolicy.Policy.Expanding, QtWidgets.QSizePolicy.Policy.Minimum)
        self.horizontalLayout.addItem(spacerItem1)
        self.pushButton = QtWidgets.QPushButton(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.pushButton.setFont(font)
        self.pushButton.setObjectName("pushButton")
        self.horizontalLayout.addWidget(self.pushButton)
        spacerItem2 = QtWidgets.QSpacerItem(40, 20, QtWidgets.QSizePolicy.Policy.Expanding, QtWidgets.QSizePolicy.Policy.Minimum)
        self.horizontalLayout.addItem(spacerItem2)
        self.pushButton_2 = QtWidgets.QPushButton(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.pushButton_2.setFont(font)
        self.pushButton_2.setObjectName("pushButton_2")
        self.horizontalLayout.addWidget(self.pushButton_2)
        spacerItem3 = QtWidgets.QSpacerItem(40, 20, QtWidgets.QSizePolicy.Policy.Expanding, QtWidgets.QSizePolicy.Policy.Minimum)
        self.horizontalLayout.addItem(spacerItem3)
        self.verticalLayout_4.addLayout(self.horizontalLayout)
        self.verticalLayout_3 = QtWidgets.QVBoxLayout()
        self.verticalLayout_3.setObjectName("verticalLayout_3")
        self.textEdit = QtWidgets.QTextEdit(parent=self.tab)
        self.textEdit.setObjectName("textEdit")
        self.verticalLayout_3.addWidget(self.textEdit)
        self.horizontalLayout_5 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_5.setObjectName("horizontalLayout_5")
        self.lineEdit_4 = QtWidgets.QLineEdit(parent=self.tab)
        self.lineEdit_4.setObjectName("lineEdit_4")
        self.horizontalLayout_5.addWidget(self.lineEdit_4)
        self.pushButton_4 = QtWidgets.QPushButton(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.pushButton_4.setFont(font)
        self.pushButton_4.setObjectName("pushButton_4")
        self.horizontalLayout_5.addWidget(self.pushButton_4)
        self.verticalLayout_3.addLayout(self.horizontalLayout_5)
        self.verticalLayout_4.addLayout(self.verticalLayout_3)
        self.verticalLayout_5.addLayout(self.verticalLayout_4)
        self.horizontalLayout_10.addLayout(self.verticalLayout_5)
        self.verticalLayout_8 = QtWidgets.QVBoxLayout()
        self.verticalLayout_8.setObjectName("verticalLayout_8")
        self.groupBox_2 = QtWidgets.QGroupBox(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.groupBox_2.setFont(font)
        self.groupBox_2.setObjectName("groupBox_2")
        self.verticalLayout_9 = QtWidgets.QVBoxLayout(self.groupBox_2)
        self.verticalLayout_9.setObjectName("verticalLayout_9")
        self.horizontalLayout_6 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_6.setObjectName("horizontalLayout_6")
        self.label_4 = QtWidgets.QLabel(parent=self.groupBox_2)
        self.label_4.setObjectName("label_4")
        self.horizontalLayout_6.addWidget(self.label_4)
        self.lineEdit_5 = QtWidgets.QLineEdit(parent=self.groupBox_2)
        self.lineEdit_5.setObjectName("lineEdit_5")
        self.horizontalLayout_6.addWidget(self.lineEdit_5)
        self.verticalLayout_9.addLayout(self.horizontalLayout_6)
        self.horizontalLayout_7 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_7.setObjectName("horizontalLayout_7")
        self.label_5 = QtWidgets.QLabel(parent=self.groupBox_2)
        self.label_5.setObjectName("label_5")
        self.horizontalLayout_7.addWidget(self.label_5)
        self.lineEdit_6 = QtWidgets.QLineEdit(parent=self.groupBox_2)
        self.lineEdit_6.setObjectName("lineEdit_6")
        self.horizontalLayout_7.addWidget(self.lineEdit_6)
        self.verticalLayout_9.addLayout(self.horizontalLayout_7)
        self.verticalLayout_8.addWidget(self.groupBox_2)
        self.verticalLayout_7 = QtWidgets.QVBoxLayout()
        self.verticalLayout_7.setObjectName("verticalLayout_7")
        self.horizontalLayout_8 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_8.setObjectName("horizontalLayout_8")
        spacerItem4 = QtWidgets.QSpacerItem(40, 20, QtWidgets.QSizePolicy.Policy.Expanding, QtWidgets.QSizePolicy.Policy.Minimum)
        self.horizontalLayout_8.addItem(spacerItem4)
        self.pushButton_5 = QtWidgets.QPushButton(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.pushButton_5.setFont(font)
        self.pushButton_5.setObjectName("pushButton_5")
        self.horizontalLayout_8.addWidget(self.pushButton_5)
        spacerItem5 = QtWidgets.QSpacerItem(40, 20, QtWidgets.QSizePolicy.Policy.Expanding, QtWidgets.QSizePolicy.Policy.Minimum)
        self.horizontalLayout_8.addItem(spacerItem5)
        self.pushButton_6 = QtWidgets.QPushButton(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.pushButton_6.setFont(font)
        self.pushButton_6.setObjectName("pushButton_6")
        self.horizontalLayout_8.addWidget(self.pushButton_6)
        spacerItem6 = QtWidgets.QSpacerItem(40, 20, QtWidgets.QSizePolicy.Policy.Expanding, QtWidgets.QSizePolicy.Policy.Minimum)
        self.horizontalLayout_8.addItem(spacerItem6)
        self.verticalLayout_7.addLayout(self.horizontalLayout_8)
        self.verticalLayout_6 = QtWidgets.QVBoxLayout()
        self.verticalLayout_6.setObjectName("verticalLayout_6")
        self.textEdit_2 = QtWidgets.QTextEdit(parent=self.tab)
        self.textEdit_2.setObjectName("textEdit_2")
        self.verticalLayout_6.addWidget(self.textEdit_2)
        self.horizontalLayout_9 = QtWidgets.QHBoxLayout()
        self.horizontalLayout_9.setObjectName("horizontalLayout_9")
        self.lineEdit_7 = QtWidgets.QLineEdit(parent=self.tab)
        self.lineEdit_7.setObjectName("lineEdit_7")
        self.horizontalLayout_9.addWidget(self.lineEdit_7)
        self.pushButton_7 = QtWidgets.QPushButton(parent=self.tab)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.pushButton_7.setFont(font)
        self.pushButton_7.setObjectName("pushButton_7")
        self.horizontalLayout_9.addWidget(self.pushButton_7)
        self.verticalLayout_6.addLayout(self.horizontalLayout_9)
        self.verticalLayout_7.addLayout(self.verticalLayout_6)
        self.verticalLayout_8.addLayout(self.verticalLayout_7)
        self.horizontalLayout_10.addLayout(self.verticalLayout_8)
        self.tabWidget.addTab(self.tab, "")
        self.tab_2 = QtWidgets.QWidget()
        self.tab_2.setObjectName("tab_2")
        self.tabWidget.addTab(self.tab_2, "")
        self.verticalLayout.addWidget(self.tabWidget)
        MainWindow.setCentralWidget(self.centralwidget)
        self.menubar = QtWidgets.QMenuBar(parent=MainWindow)
        self.menubar.setGeometry(QtCore.QRect(0, 0, 957, 22))
        self.menubar.setObjectName("menubar")
        MainWindow.setMenuBar(self.menubar)
        self.statusbar = QtWidgets.QStatusBar(parent=MainWindow)
        font = QtGui.QFont()
        font.setPointSize(11)
        self.statusbar.setFont(font)
        self.statusbar.setObjectName("statusbar")
        MainWindow.setStatusBar(self.statusbar)

        self.retranslateUi(MainWindow)
        self.tabWidget.setCurrentIndex(0)
        QtCore.QMetaObject.connectSlotsByName(MainWindow)

    def retranslateUi(self, MainWindow):
        _translate = QtCore.QCoreApplication.translate
        MainWindow.setWindowTitle(_translate("MainWindow", "MainWindow"))
        self.groupBox.setTitle(_translate("MainWindow", "服务器配置:"))
        self.label.setText(_translate("MainWindow", "服务端IP地址:"))
        self.lineEdit.setText(_translate("MainWindow", "127.0.0.1"))
        self.pushButton_3.setText(_translate("MainWindow", "使用本机IP地址"))
        self.label_2.setText(_translate("MainWindow", "服务器端口:"))
        self.lineEdit_2.setText(_translate("MainWindow", "12000"))
        self.pushButton.setText(_translate("MainWindow", "启动服务"))
        self.pushButton_2.setText(_translate("MainWindow", "停止服务"))
        self.pushButton_4.setText(_translate("MainWindow", "发送"))
        self.groupBox_2.setTitle(_translate("MainWindow", "客户端配置"))
        self.label_4.setText(_translate("MainWindow", "服务器IP:"))
        self.lineEdit_5.setText(_translate("MainWindow", "127.0.0.1"))
        self.label_5.setText(_translate("MainWindow", "服务器端口:"))
        self.lineEdit_6.setText(_translate("MainWindow", "12000"))
        self.pushButton_5.setText(_translate("MainWindow", "连接服务器"))
        self.pushButton_6.setText(_translate("MainWindow", "断开连接"))
        self.pushButton_7.setText(_translate("MainWindow", "发送"))
        self.tabWidget.setTabText(self.tabWidget.indexOf(self.tab), _translate("MainWindow", "TCP协议"))
        self.tabWidget.setTabText(self.tabWidget.indexOf(self.tab_2), _translate("MainWindow", "UDP协议"))

五、application.py 启动代码

import os
import sys
from module.main import MainWindow
from PyQt6.QtWidgets import QApplication

if __name__ == '__main__':
    app = QApplication(sys.argv)
    login = MainWindow()
    sys.exit(app.exec())

六、main.py 代码


from PyQt6 import QtWidgets
from .server import Server
from .client import Client
from ui.ui_Main import Ui_MainWindow


class MainWindow(QtWidgets.QMainWindow, Ui_MainWindow):
    """
        主窗口初始化
    """

    def __init__(self):
        super(MainWindow, self).__init__()
        self.setupUi(self)
        self.show()

        self.pushButton.clicked.connect(self.server_start)
        self.pushButton_2.clicked.connect(self.server_stop)
        self.pushButton_4.clicked.connect(self.server_send_data)

        self.pushButton_5.clicked.connect(self.client_connect_server)
        self.pushButton_6.clicked.connect(self.client_disconnect_server)
        self.pushButton_7.clicked.connect(self.client_send_data)

        self.server = None
        self.client = None

    def client_connect_server(self):
        server_ip = self.lineEdit_5.text()
        server_port = int(self.lineEdit_6.text())
        client_name = '客户端'
        self.client = Client(self, server_ip, client_name, server_port)

    def client_disconnect_server(self):
        self.client.stop()

    def client_send_data(self):
        message = self.lineEdit_7.text()
        self.client.send_data(message)

    def server_start(self):
        server_ip = self.lineEdit.text()
        server_port = int(self.lineEdit_2.text())
        server_name = '服务器'
        self.server = Server(self, server_ip, server_name, server_port)

    def server_stop(self):
        self.server.stop()

    def server_send_data(self):
        message = self.lineEdit_4.text()
        self.server.send_message_to_client(message)

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/217951.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

JS浮点数精度问题及解决方案

前端面试大全JS浮点数精度问题及解决方案 🌟经典真题 🌟浮点数精度常见问题 🌟为什么会有这样的问题 🌟真题解答 🌟总结 🌟经典真题 为什么 console.log(0.20.10.3) 得到的值为 false 🌟…

Spring Security 6.x 系列(9)—— 基于过滤器链的源码分析(二)

一、前言 在本系列文章: Spring Security 6.x 系列(4)—— 基于过滤器链的源码分析(一)中着重分析了Spring Security在Spring Boot 的自动配置、 DefaultSecurityFilterChain 的构造流程、FilterChainProxy 的构造流…

12.4 C++ 作业

完成沙发床的多继承 #include <iostream>using namespace std;//封装 沙发 类 class Sofa { private:string *sitting; public://无参构造函数Sofa(){cout << "Sofa::无参构造函数" << endl;}//有参构造函数Sofa(string s):sitting(new string(s)…

手机升级到iOS15.8后无法在xcode(14.2)上真机调试

之前手机是iOS14.2的系统,在xcode上进行真机测试运行良好&#xff0c;因为想要使用Xcode的Instruments功能&#xff0c;今天将系统更新到了iOS15.8 &#xff0c;结果崩了 说是Xcode和手机系统不兼容不能进行真机测试。在网上查不好些方法&#xff0c;靠谱的就是下载相关版本的…

C语言小游戏:三子棋

目录 &#x1f30d;前言 &#x1f685;目录设计 &#x1f48e;游戏逻辑设置 ⚔三子棋棋盘设计 ⚔三子棋运行逻辑 &#x1f440;怎么设置人下棋 &#x1f440;怎么设置电脑下棋 ✈如何判断输赢 ✍结语 &#x1f30d;前言 Hello,csdn的各位小伙伴你们好啊!这次小赵给大…

ArcGIS平滑处理栅格数据

一、实验背景 基于栅格数据的空间分析&#xff0c;常常需要根据特定的分析场景对栅格数据进行处理&#xff0c;如栅格数据的噪声处理。噪声是属性值具有突跃特征的像元位置&#xff0c;直接对带有噪声的栅格数据进行分析会对结果造成较大的影响。而降噪的主要方法之一是平滑&a…

12.4_黑马MybatisPlus笔记(下)

目录 11 12 thinking&#xff1a;关于Mybatis Plus中BaseMapper和IService&#xff1f; 13 ​编辑 thinking&#xff1a;CollUtil.isNotEmpty? 14 thinking&#xff1a;Collection、Collections、Collector、Collectors&#xff1f; thinking&#xff1a;groupBy&#…

风格迁移网络修改流程(自用版)

一. AdaAttN-Revisit Attention Mechanism in Arbitrary Neural Style Transfer&#xff08;ICCV2021&#xff09; 下载vgg_normalised.pth打开visdom python -m visdom.server在 train_adaattn.sh 中配置 content_path、style_path 和 image_encoder_path&#xff0c;分别表…

FFmpeg在Centos服务器上离线安装(包含所需依赖)并实现拉取rtsp流与推送至rtmp服务器

场景 Windows上使用FFmpeg实现rtsp视频流推流到RTMP流媒体服务器(EasyCVR流媒体服务器)&#xff1a; Windows上使用FFmpeg实现rtsp视频流推流到RTMP流媒体服务器(EasyCVR流媒体服务器)_rtsp 转流-CSDN博客 上面讲了在windows上ffmpeg的应用示例&#xff0c;如果是在centos服…

Hadoop进阶学习---HDFS分布式文件存储系统

1.hdfs分布式文件存储的特点 分布式存储:一次写入,多次读取 HDFS文件系统可存储超大文件,时效性较差. HDFS基友硬件故障检测和自动快速恢复功能. HDFS为数据存储提供很强的扩展能力. HDFS存储一般为一次写入,多次读取,只支持追加写入,不支持随机修改. HDFS可以在普通廉价的机器…

canvas绘制小丑

说明&#xff1a; 借鉴博主基于canvas绘制一个爱心(10行代码就够了) - 掘金 (juejin.cn) 代码实现 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta http-equiv"X-UA-Compatible" content&quo…

震坤行2023安全月活动顺利收官

震坤行2023安全月活动顺利收官 2023年6月&#xff0c;是第22个全国“安全生产月”&#xff0c;主题为 “人人讲安全、个个会应急”。震坤行工业超市(上海)有限公司基于国家 “安全生产月”的主题要求&#xff0c;以及公司具体的安全形势&#xff0c;于6月1日在全公司范围内正式…

EM32DX-E4【C#】

1外观&#xff1a; ecat总线&#xff0c;分布式io 2电源&#xff1a; 靠近SW拨码&#xff1a;24V 中间&#xff1a;0V 靠近面板&#xff1a;PE接地 3DI&#xff1a; 6000H DI输入寄存器 16-bit &#xff08;16位输入&#xff09; 00H U8 子索引总数 01H Unsigned16 IN1…

TCP 半连接队列和全连接队列

在 TCP 三次握手的时候&#xff0c;Linux 内核会维护两个队列&#xff0c;分别是&#xff1a; 半连接队列&#xff0c;也称 SYN 队列&#xff1b; 全连接队列&#xff0c;也称 accept 队列&#xff1b; 服务端收到客户端发起的 SYN 请求后&#xff0c;内核会把该连接存储到半连…

数据库系统概论期末经典大题讲解(用关系代数进行查询)

今天也是结束的最为密集的考试周&#xff0c;在分析过程中自己也有些许解题的感悟&#xff0c;在此分享出来&#xff0c;希望能帮到大家期末取得好成绩。 一.专门的关系运算 1.选择&#xff08;σ&#xff09; 选择操作符用于从关系中选择满足特定条件的元组 例如&#xff0c;…

计算机组成原理学习-总线总结

复习本章时&#xff0c;思考以下问题&#xff1a; 1)引入总线结构有什么好处&#xff1f;2)引入总线结构会导致什么问题&#xff1f;如何解决&#xff1f;

【专题】【中值定理-还原大法】

1&#xff09;构造辅助函数 2&#xff09;罗尔定理&#xff1a; 闭区间连续&#xff0c;开区间可导 F&#xff08;a&#xff09;F&#xff08;b&#xff09; 3&#xff09;F‘&#xff08;ξ&#xff09;0&#xff0c;原命题得证 极限保号性&#xff1a;

WPS论文写作——公式和公式序号格式化

首先新建一个表格&#xff0c;表格尺寸按你的需求来确定&#xff0c;直接 插入--》表格 即可。 然后在表格对应位置填上公式&#xff08;公式要用公式编辑器&#xff09;和公式序号&#xff0c;然后可以按照单独的单元格或者整行或整列等来设置样式&#xff0c;比如居中对齐、…

微服务实战系列之Cache(技巧篇)

前言 凡工具必带使用说明书&#xff0c;如不合理的使用&#xff0c;可能得到“意外收获”。这就好比每个人擅长的领域有所差异&#xff0c;如果放错了位置或用错了人&#xff0c;也一定会让 Leader 们陷入两难之地&#xff1a;“上无法肩负领导之重托&#xff0c;下难免失去伙伴…

123456前端调AES加密方法变为YehdBPev

使用密码加密服务: pig4cloud 加密服务