首页 > 解决方案 > socket.send 和 socket.sendall() 的区别

问题描述

我编写了两个程序来测试服务器端的 p23_server.py 和客户端的 p23_client.py :

p23_server.py

#p23_server.py
import socket

HOST = '10.0.2.15'
PORT = 12345

server = socket.socket()
server.bind((HOST,PORT))
server.listen(1)
(client,addr) = server.accept()
while True:
    data = client.recv(32)
    if not data:
        break
    print(data.decode('utf-8'))
server.close()

p23_client.py

#p23_client.py
import socket
import sys

HOST = '10.0.2.15'
PORT = 12345

string = sys.argv[1]
data_to_send = string.encode('utf-8')


s = socket.socket()
s.connect((HOST,PORT))
#s.sendall(data_to_send)
s.send(data_to_send)
s.close()

我运行 p23_server.py 然后执行命令:

wahalez@wahalez:~/dev/python$ python p23_client.py $(python -c 'for i in range(1024): print("a",end="")')

运行客户端并查看服务器输出的内容。

我用 socket.send() 和 socket.sendall() 函数执行了一次。结果是一样的。问题是为什么?不应该只发送一次数据,然后服务器收到 32 个字节,就是这样?

与 send() 不同,此方法继续从字节发送数据,直到所有数据都已发送或发生错误。成功时不返回任何内容。出错时会引发异常,并且无法确定成功发送了多少数据(如果有)。

为什么这两个函数产生相同的结果?

标签: pythonsocketspython-sockets

解决方案


仅仅因为 99% 的时间 send() 将设法一次性发送所有数据。从理论上讲,当您使用 send() 时,您可能看不到服务器上的所有数据。

为了强调区别,sendall 的示例伪实现:

def sendall(data):
    already_sent = 0
    while already_sent < len(data):
        already_sent += send(data[already_sent:])

推荐阅读