黏包以及解决
Posted zhigu
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了黏包以及解决相关的知识,希望对你有一定的参考价值。
1 import struct 2 ret = struct.pack(‘i‘, 11111111) #把一串数据转化成长度为4的字节 3 print(ret, len(ret)) #b‘xc7x8axa9x00‘ 4 4 num = struct.unpack(‘i‘, ret) 5 print(num) #(11111111,) 返回的是一个元组,所以要取第一个 6 print(num[0]) #11111111
黏包:同时执行多条命令之后,得到的结果很有可能只有一部分,在执行其他命令的时候又接收到之前执行的另外一部分结果,这种显现就叫做黏包
1 #server 2 import socket 3 sk = socket.socket() 4 sk.bind((‘127.0.0.1‘, 8888)) 5 sk.listen() 6 conn, addr = sk.accept() 7 conn.send(b‘hello,‘) 8 conn.send(b‘world‘) 9 conn.close() 10 sk.close() 11 12 #client 13 import socket 14 sk = socket.socket() 15 sk.connect((‘127.0.0.1‘, 8888)) 16 ret1 = sk.recv(4) 17 print(ret1) #b‘hell‘ 18 ret2 = sk.recv(1024) 19 print(ret2) #b‘o,‘ 传输的内容与速度有关 20 sk.close() 21 22 #client 23 import socket 24 sk = socket.socket() 25 sk.connect((‘127.0.0.1‘, 8888)) 26 ret1 = sk.recv(1024) 27 print(ret1) #b‘hello,‘ 28 ret2 = sk.recv(1024) 29 print(ret2) #b‘world‘ 30 sk.close()
同时执行多条命令,会产生合包和拆包现象
合包现象:数据很短 时间间隔很短
拆包现象:数据大的时候会发生拆分 不会一次性的全部发送给对方
对方在接收的时候很可能没有办法一次性接收到所有的信息
那么没有接受完的信息很可能和后面的信息黏在一起
黏包现象只发生在TCP协议:
tcp协议的传输是 流式传输 ,每一条信息与信息之间是没有边界的
UDP协议中是不会发生黏包现象的:
适合短数据的发送,不建议发送过长的数据,会增大数据丢失的几率
在程序中出现黏包的原因:收发数据的边界不清晰 接收数据的这一端不知道接收数据的长度到底是多少
1 #server 2 import socket 3 import struct #引用struct模块,将一个数据(不论长度)打包成一个4长度 4 sk = socket.socket() 5 sk.bind((‘127.0.0.1‘, 8899)) 6 sk.listen() 7 conn, addr = sk.accept() 8 while True: 9 st_msg = input(‘>>>‘).encode(‘utf-8‘) 10 ret = struct.pack(‘i‘, len(st_msg)) #把要传送的内容打包 11 conn.send(ret) #把包传过去 12 conn.send(st_msg) #把包里的内容传过去 13 conn.close() 14 sk.close() 15 #client 16 import socket 17 import struct 18 sk = socket.socket() 19 sk.connect((‘127.0.0.1‘, 8899)) 20 while True: 21 pack_num = sk.recv(4) #接收长度为4的包 22 num = struct.unpack(‘i‘, pack_num)[0] #打开包。取包里第一组数字 23 ret = sk.recv(num) #接收和数字等长度的内容 24 print(ret.decode(‘utf-8‘)) #打印此内容 25 sk.close()
以上是关于黏包以及解决的主要内容,如果未能解决你的问题,请参考以下文章