Python UDP 套接字在第一次连接后不工作

Python UDP socket don't work after making first connection

我正在训练在 python 上制作简单的应用程序,该应用程序使用套接字并使用 UDP 协议。我有一个 client.py 和 server.py。我想在无限循环中将消息从客户端发送到服务器并从服务器捕获响应消息。为此,我有以下代码:

server.py

import socket

serversocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
host = "127.0.0.1"
port = 8000
print(host)
print(port)
serversocket.bind((host, port))

serversocket.listen(5)
print('server started and listening')
while 1:
    (clientsocket, address) = serversocket.accept()
    print("connection found!")
    data = clientsocket.recv(1024).decode()
    print(data)
    r = 'I can hear you by UDP!!!!'
    clientsocket.send(r.encode())

client.py

import socket

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
host = "127.0.0.1"
port = 8000
addr = (host, port)
s.connect(addr)


def send(user_input):
    s.sendto(user_input.encode(), addr)
    data = s.recv(1024).decode()
    print('Server tell that: ', data)


while 1:
    if input('Exit? (y/n)') == 'y':
        break
    i = input('>> ')
    send(i)

s.close()

它工作正常,但是当我第二次尝试发送消息时,我的程序在线停止

s.sendto(user_input.encode(), addr)

我不明白此刻发生了什么。

如果您想为 UDP 构建 server/client,您需要仔细阅读文档以防止使用用于 connection-oriented 协议的 API。

下面是一个 UDP 的工作示例:(我在代码中添加了一些注释,然后你就会明白为什么要调整它们)。

服务器:

对于一台UDP服务器,您需要使用一个套接字socket.SOCK_DGRAM而不是SOCK_STREAM进行初始化,然后绑定您想要的端口。

import socket

#The type of communications between the two endpoints, typically SOCK_STREAM for connection-oriented protocols and SOCK_DGRAM for connectionless protocols.
serversocket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
host = "127.0.0.1"
port = 8000
print(host)
print(port)
serversocket.bind((host, port))

#serversocket.listen(5)  #--This method sets up and start TCP listener.
print('server started and listening')
while 1:
    #(clientsocket, address) = serversocket.accept() #---This passively accept TCP client connection, waiting until connection arrives (blocking)
    #print("connection found!")
    #data = clientsocket.recv(1024).decode() #This method receives TCP message
    data, addr = serversocket.recvfrom(2048)
    print(data)
    r = 'I can hear you by UDP!!!!'
    serversocket.sendto(r.encode(), addr)
serversocket.close()

客户:

对于一个UDP客户端,你需要用socket.SOCK_DGRAM而不是SOCK_STREAM初始化一个套接字,然后使用sendto将数据发送到服务器。

import socket
#The type of communications between the two endpoints, typically SOCK_STREAM for connection-oriented protocols and SOCK_DGRAM for connectionless protocols.
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
host = "127.0.0.1"
port = 8000
addr = (host, port)
#s.connect(addr) #---This method actively initiates TCP server connection.


def send(user_input):
    s.sendto(user_input.encode(), addr)
    data = s.recvfrom(1024).decode()
    print('Server tell that: ', data)


while 1:
    if input('Exit? (y/n)') == 'y':
        break
    i = input('>> ')
    send(i)

s.close()

更多详情:

勾选Python Socket