Python网络编程基于多线程实现多用户全双工聊天功能示例

Python网络编程基于多线程实现多用户全双工聊天功能示例

什么是Python网络编程?

Python网络编程是指使用Python语言编写网络应用程序的技术。在Python网络编程中,使用Python标准库中的socket库来实现网络通信,通过socket库提供的接口,可以在不同的计算机之间建立连接,传输数据等。

多线程实现多用户全双工聊天功能

使用多线程可以实现多个用户同时聊天的功能,同时支持全双工通信,即不同用户之间可以同时发送和接收消息。

下面是一个示例代码:

import socket
import threading

# 服务器配置
SERVER_HOST = '0.0.0.0'
SERVER_PORT = 8000
BUFSIZ = 1024

# 创建socket
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server_socket.bind((SERVER_HOST, SERVER_PORT))
server_socket.listen(5)
print('Server listening on {}:{}'.format(SERVER_HOST, SERVER_PORT))

# 保存连接的客户端socket列表
clients = []

# 处理客户端socket的函数
def handle_client(client_socket):
    while True:
        try:
            # 接收消息
            msg = client_socket.recv(BUFSIZ)
            if not msg:
                # 客户端断开连接
                print('Client disconnected')
                clients.remove(client_socket)
                client_socket.close()
                break
            # 广播消息给其他所有客户端
            for client in clients:
                client.send(msg)
        except Exception as e:
            print('Socket error: {}'.format(str(e)))

# 主循环,接受客户端连接
while True:
    client_socket, client_address = server_socket.accept()
    print('New client connected: {}:{}'.format(client_address[0], client_address[1]))
    clients.append(client_socket)
    # 创建一个新的线程处理客户端socket
    client_thread = threading.Thread(target=handle_client, args=(client_socket,))
    client_thread.start()

在此示例中,我们首先创建服务器socket并绑定到指定的HOST和PORT,然后使用listen方法等待客户端连接。

一旦有客户端连接进来,服务器就会创建一个新的线程来处理该客户端socket,同时将客户端socket保存到clients列表中,方便后续广播消息给所有客户端。

handle_client函数的实现非常简单,它负责处理特定客户端的所有通信。在一个无限循环中,它首先使用recv方法接收客户端发送的消息,如果接收到消息为空,就说明客户端已经断开连接,我们可以将其socket从clients列表中移除并关闭该socket,同时退出循环。否则,将收到的消息广播给clients列表中的所有其他客户端。

这种方式可以让我们实现一个简单的多用户全双工聊天应用。

示例说明

示例一:客户端和服务器在同一台机器上

假设我们已经在本地机器上搭建了一个TCP服务器,IP地址为127.0.0.1,端口号为8000。现在我们需要使用一个客户端连接到该服务器并进行聊天。

import socket

SERVER_HOST = '127.0.0.1'
SERVER_PORT = 8000
BUFSIZ = 1024

client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
client_socket.connect((SERVER_HOST, SERVER_PORT))

while True:
    msg = input('Enter message to send:')
    client_socket.send(bytes(msg, 'utf-8'))
    data = client_socket.recv(BUFSIZ)
    print('Received from server:', data.decode('utf-8'))

在上面的代码中,我们创建了一个新的客户端socket,并使用connect方法连接到指定的服务器,之后进入一个无限循环中,等待用户输入消息并将其发送给服务器。接着等待服务器发送回应,在控制台输出收到的消息。

示例二:客户端和服务器在不同的机器上

假设我们需要在两台机器之间进行聊天,一台机器作为服务器,另一台机器作为客户端。假设服务器的IP地址是192.168.0.100,端口号为8000,客户端的IP地址是192.168.0.101。以下是客户端的示例代码:

import socket

SERVER_HOST = '192.168.0.100'
SERVER_PORT = 8000
BUFSIZ = 1024

client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
client_socket.connect((SERVER_HOST, SERVER_PORT))

while True:
    msg = input('Enter message to send:')
    client_socket.send(bytes(msg, 'utf-8'))
    data = client_socket.recv(BUFSIZ)
    print('Received from server:', data.decode('utf-8'))

客户端的代码与示例一的代码相同,唯一的区别是SERVER_HOST变量的值。

服务器的代码与示例一的代码相同,唯一的区别在于通过主机名或IP地址来指定绑定的HOST。

import socket
import threading

# 服务器配置
SERVER_HOST = '0.0.0.0'  # 这里使用0.0.0.0表示可以绑定任意IP地址
SERVER_PORT = 8000
BUFSIZ = 1024

# 创建socket
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server_socket.bind((SERVER_HOST, SERVER_PORT))
server_socket.listen(5)
print('Server listening on {}:{}'.format(SERVER_HOST, SERVER_PORT))

# 保存连接的客户端socket列表
clients = []

# 处理客户端socket的函数
def handle_client(client_socket):
    while True:
        try:
            # 接收消息
            msg = client_socket.recv(BUFSIZ)
            if not msg:
                # 客户端断开连接
                print('Client disconnected')
                clients.remove(client_socket)
                client_socket.close()
                break
            # 广播消息给其他所有客户端
            for client in clients:
                client.send(msg)
        except Exception as e:
            print('Socket error: {}'.format(str(e)))

# 主循环,接受客户端连接
while True:
    client_socket, client_address = server_socket.accept()
    print('New client connected: {}:{}'.format(client_address[0], client_address[1]))
    clients.append(client_socket)
    # 创建一个新的线程处理客户端socket
    client_thread = threading.Thread(target=handle_client, args=(client_socket,))
    client_thread.start()

注意,这里的SERVER_HOST变量是绑定到服务器网卡的IP地址。如果服务器有多个网卡,您需要确定要使用哪个IP地址来绑定,才能实现正确的通信。

综上所述,本文介绍了Python网络编程中基于多线程实现多用户全双工聊天功能的实现方法,并提供了两个示例说明。通过这些示例,您可以快速掌握Python网络编程的基本技巧,为您的网络编程之旅打下坚实的基础。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:Python网络编程基于多线程实现多用户全双工聊天功能示例 - Python技术站

(0)
上一篇 2023年5月19日
下一篇 2023年5月19日

相关文章

  • 深入浅析Python 中的sklearn模型选择

    深入浅析Python 中的sklearn模型选择 本文将针对Python中的scikit-learn (简称 sklearn),深入浅出的介绍模型选择的相关知识。 什么是模型选择 在机器学习中,模型选取是一个非常重要的工作。机器学习算法存在许多参数需要调整,而这些参数的不同取值会对最终的模型性能产生非常大的影响。模型选择的目的是在不同的模型或不同的参数集上进…

    python 2023年6月2日
    00
  • Python+Xlwings 删除Excel的行和列

    下面是详细的讲解。 Python+Xlwings删除Excel的行和列 Python是一种功能强大的语言,可以帮助用户自动化许多重复性的工作,而 Excel 是广泛使用的办公软件,它提供了一个基于工作簿和工作表的视图,可以帮助您分析和呈现数据。有时我们需要在 Excel 中删除一些行和列,这时候我们可以使用 Python 和 xlwings 库来实现。 st…

    python 2023年5月13日
    00
  • python os模块介绍

    Python os模块介绍 简介 在Python中,os模块是用于与操作系统进行交互的模块,它提供了很多与操作系统相关的功能。 常用功能 获取当前工作目录 使用os模块中的getcwd()函数可以获取当前工作目录。 import os cwd = os.getcwd() print(cwd) 创建目录 使用os模块中的mkdir()函数可以创建目录。 imp…

    python 2023年5月30日
    00
  • python处理json文件的四个常用函数

    当我们需要处理 JSON 格式的数据时,Python 中提供了很多有用的函数。本文将介绍 Python 处理 JSON 文件的四个常用函数:load()、loads()、dump() 和 dumps()。 load() load() 函数可以将 JSON 文件加载为 Python 中的一个对象。对于大型的 JSON 文件,我们可以使用这个函数以避免将文件一次…

    python 2023年6月3日
    00
  • 读取许多 csv 文件并使用 python 将其写入编码为 utf8

    【问题标题】:Read many csv file and write it to encoding to utf8 using python读取许多 csv 文件并使用 python 将其写入编码为 utf8 【发布时间】:2023-04-05 23:04:01 【问题描述】: 我正在使用 python 代码从许多 csv 文件中读取并将编码设置为 utf…

    Python开发 2023年4月6日
    00
  • 实现Python3数组旋转的3种算法实例

    以下是关于“实现Python3数组旋转的3种算法实例”的完整攻略: 简介 数组旋转是一种常见的操作,它可以将数组中的元素按照一定的规则进行旋转。本教程将介绍三种不同的算法,用Python3实现数组旋转,并提供两个示例。 算法1:暴力法 暴力法是一种简单的算法,它通过多次旋转单个元素来实现数组旋转。具体来说,我们可以使用两个嵌套的循环,将数组中的每个元素旋转k…

    python 2023年5月14日
    00
  • pip报错“TypeError: ‘NoneType’ object is not callable”怎么处理?

    当使用 pip 安装 Python 包时,可能会遇到 “TypeError: ‘NoneType’ object is not callable” 错误。这个错误通常是由于 Python 模块导入问题导致的。以下是详细讲解 pip 报错 “TypeError: ‘NoneType’ object is not callable” 的原因与解决办法,包含两条实…

    python 2023年5月4日
    00
  • python微信跳一跳系列之自动计算跳一跳距离

    下面是“Python微信跳一跳系列之自动计算跳一跳距离”的完整攻略。 简介 可能大家都玩过微信跳一跳游戏,在这个游戏中,我们需要让跳跃的小人跳跃到合适的位置,让他落在方块上,以此获得分数。这个游戏看似简单,但真正掌握技巧和实现高分却并不容易。 而自动计算跳一跳距离,则是为了让玩家在支付宝或者微信中能够轻松获得高分,这就需要使用Python来实现自动计算。 在…

    python 2023年6月3日
    00
合作推广
合作推广
分享本页
返回顶部