struct 模块
# ### struct 模块使用
import struct
"""
pack 打包
把任意长度数字转换成具有固定4个字节长度的字节流
unpack 解包
把4个字节长度的值恢复成原来的数字,返回元组
"""
# pack
# i => int 要转换的当前类型是整型
"""范围: -21亿~21亿左右 控制在1.8G之内"""
res = struct.pack("i" , 999999998)
print(res , len(res))
res = struct.pack("i" , 1111111119)
print(res , len(res))
res = struct.pack("i" , 3)
print(res , len(res))
res = struct.pack("i" , 2000000000)
print(res , len(res))
# unpack
# i => 把对应的数据转化成整型
tup = struct.unpack("i" , res)
print(tup) #(2000000000,)
print(tup[0])
"""
#解决黏包场景:
应用场景在实时通讯时,需要阅读此次发的消息是什么
#不需要解决黏包场景:
下载或者上传文件的时候,最后要把包都结合在一起,黏包无所谓.
"""
server 服务端
import socket
import time
import struct
"""
黏包现象:
(1)发送端,数据小,时间间隔短,造成黏包
(2)接收端,没有及时接受数据,可能把多次发送的数据当成一条截取.
"""
sk = socket.socket()
sk.setsockopt(socket.SOL_SOCKET,socket.SO_REUSEADDR,1)
sk.bind( ("127.0.0.1",9001) )
sk.listen()
conn,addr = sk.accept()
# 收发数据的逻辑
strvar = input("[服务端]请输入您要发送的数据")
msg = strvar.encode()
length = len(msg)
res = struct.pack("i",length)
# 第一次发送数据 (数据长度)
conn.send(res)
# 第二次发送数据 (真实数据)
conn.send(msg)
# 第三次发送数据 (真实数据)
conn.send(b"world,hello")
conn.close()
sk.close()
client 客户端
import socket
import time
import struct
sk = socket.socket()
sk.connect( ("127.0.0.1",9001) )
time.sleep(2)
# 收发数据的逻辑
# 第一次接受数据 (数据长度)
num = sk.recv(4)
tup = struct.unpack("i",num)
print(tup[0])
# 第二次接受数据 (真实数据)
res = sk.recv(tup[0])
print(res.decode())
# 第三次接受数据 (真实数据)
res = sk.recv(1024)
print(res.decode())
sk.close()