一:什么是socket大数据包发送问题
socket服务器端或者客户端在向对方发送的数据大于对方接受的缓存时,会出现第二次接受还接到上次命令发送的结果。这就出现象第一次接受结果不全,第二次接果出现第一次结果。
比如send 1900 数据,recv 只接受1024。多于数据900放在缓存区里,第二次命令来的时候,调用send会先把900发回去,在把新数据放到缓存区,等到1024在系统会自动发送过去。
发送数据,一是缓存区满,二是超时
解决办法:
在发送数据前,计算发送数据的大小,把大小发给对方。对方接受数据循环,只到接到数据和大小一样。
二:示例代码
服务器 # -*- coding:utf-8 -*- __author__ = ‘shisanjun‘ import socket import subprocess server=socket.socket() server.bind(("127.0.0.1",9999)) server.listen(5) while True: conn,addr=server.accept() print("new conn:",addr) while True: print(addr) data=conn.recv(1024) print(len(data)) print(data.decode()) if not data: print("conn close ",addr) break print(data.decode()) cmd_res=subprocess.Popen(data.decode(),shell=True,stdout=subprocess.PIPE) outread=cmd_res.stdout.read() print(outread.decode("gb2312")) conn.send(outread)
客户端 # -*- coding:utf-8 -*- __author__ = ‘shisanjun‘ import socket client=socket.socket() client.connect(("127.0.0.1",9999)) while True: cmd=input(">>:").strip() if len(cmd)==0:continue print(cmd) client.send(cmd.encode("utf-8")) print("res") res=client.recv(1024) print(res.decode("gb18030"))
大数据发送结果乱问题现象截图:
三:解决代码如下:
服务器端 # -*- coding:utf-8 -*- __author__ = ‘shisanjun‘ import socket import subprocess server=socket.socket() server.bind(("127.0.0.1",9999)) server.listen(5) while True: conn,addr=server.accept() print("new conn:",addr) while True: print(addr) data=conn.recv(1024) print(len(data)) print(data.decode()) if not data: print("conn close ",addr) break print(data.decode()) cmd_res=subprocess.Popen(data.decode(),shell=True,stdout=subprocess.PIPE) outread=cmd_res.stdout.read() print(len(outread)) conn.send(("%s" %len(outread)).encode("utf-8")) print(outread.decode("gb2312")) conn.send(outread)
# -*- coding:utf-8 -*- __author__ = ‘shisanjun‘ import socket client=socket.socket() client.connect(("127.0.0.1",9999)) while True: cmd=input(">>:").strip() if len(cmd)==0:continue print(cmd) client.send(cmd.encode("utf-8")) print("res") res_size=client.recv(1024).decode("utf-8") size=0 while size<int(res_size): res=client.recv(1024) print(res.decode("gb18030")) size+=len(res) #这里要用len(),因为最后一次长度不固定
时间: 2024-10-10 13:45:23