Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/multithreading/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 如何为所有线程指定一个新变量?_Python_Multithreading_Sockets_Server - Fatal编程技术网

Python 如何为所有线程指定一个新变量?

Python 如何为所有线程指定一个新变量?,python,multithreading,sockets,server,Python,Multithreading,Sockets,Server,我制作了一个类似于游戏聊天的程序,玩家可以在其中聊天,服务器所有者可以广播一条消息(来自服务器的机器) 因此,到目前为止的代码是: import socket import threading HEADER = 64 PORT = 5050 SERVER = "192.168.0.100" ADDR = (SERVER, PORT) FORMAT = 'utf-8' DISCONNECT_MESSAGE = "!DISCONNECT" server =

我制作了一个类似于游戏聊天的程序,玩家可以在其中聊天,服务器所有者可以广播一条消息(来自服务器的机器)

因此,到目前为止的代码是:

import socket
import threading

HEADER = 64
PORT = 5050
SERVER = "192.168.0.100"
ADDR = (SERVER, PORT)
FORMAT = 'utf-8'
DISCONNECT_MESSAGE = "!DISCONNECT"

server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server.bind(ADDR)

def handle_client(conn, addr):
    print(f"[NEW CONNECTION] {addr} connected.")

    connected = True
    while connected:
        msg_lenght = conn.recv(HEADER).decode(FORMAT)
        if msg_lenght:
            msg_lenght = int(msg_lenght)
            msg = conn.recv(msg_lenght).decode(FORMAT)
            if msg == DISCONNECT_MESSAGE:
                connected = False

            else:
                print(f"[{addr}] {msg}")
    
    conn.close()

def start():
    server.listen()
    print(f"[LISTENING] Sever is listening on {SERVER}")
    while True:
        conn, addr = server.accept()
        thread = threading.Thread(target=handle_client, args=(conn, addr))
        thread.start()
        print(f"[ACTIVE CONNECTIONS] {threading.activeCount() - 1}")

print("[STARTING] Starting......")
start()
这是服务器端代码。我很难添加服务器所有者可以广播消息的部分。(我不想增加球员可以私下交谈的部分)

因此,我的问题是,在呼叫时,如何区分客户机?

conn, addr = server.accept()
对于基于IP的网络,返回的
addr
是一个元组,由客户端的IP地址或域名、客户端上用于连接的端口号以及可能的其他数据组成


元组内容对于特定的客户端连接是唯一的,可用于区分连接。

一种简单的方法是将可变容器作为参数传递给
handle\u client
函数,并使其包含所有活动连接。您至少可以使用包含已连接套接字的列表,并使用互斥锁对其进行保护:

lock = threading.Lock()

def handle_client(conn, addr, connections):
    print(f"[NEW CONNECTION] {addr} connected.")
    with lock:
        connections.append(conn)
    ...
    conn.close()
    with lock
        connections.remove(conn)

def start():
    server.listen()
    print(f"[LISTENING] Sever is listening on {SERVER}")
    connections = []
    while True:
        conn, addr = server.accept()
        thread = threading.Thread(target=handle_client, args=(conn, addr, connections))
这样,在handleclient中,您有一个所有活动连接的列表,该列表可用于广播消息


如果您想方便地允许用户交换消息,您还可以为每个连接指定一个唯一的id,并将该id用作
连接
字典的键。

由“socket.accept”返回的地址元组对于每个客户端都是不同的。噢,我很早就错过了这个细节,谢谢您告诉我,你能把它作为答案,这样我可以勾选它吗?Lock()做什么?如果我必须广播一条消息,我将如何做?比如我要为它开始一个新的线程吗?(但这使得如果
连接
获得任何新的
连接
,那么它将无法获得改进版的
连接
),或者只是创建一个具有管理员权限的新客户端?(但这无助于我提高编码技能)