11 1 socket連線中的粘包 精確傳輸問題

2022-01-31 17:07:04 字數 2824 閱讀 3500

當呼叫send的時候,資料並不是即時發給客戶端的。而是放到了系統的socket傳送緩衝區裡,等緩衝區滿了、或者資料等待超時了,資料才會傳送,所以有時候傳送太快的話,前乙份資料還沒有傳給客戶端,那麼這份資料和上乙份資料一起發給客戶端的時候就會造成「粘包」 。

解決根源的思想是避免不同段的資料一起傳送。

方案1:前一段資料send完後,等待一段時間再send第二段資料。缺點:時間效率低,而且也無法完全避免問題【因為不清楚該設定多少時間才能保證前乙份資料已經傳送】

方案2:握手機制:前一段資料send完後,嘗試recv,等待客戶端回應,確認第一段資料傳送完後,再send第二段資料。完美方案?

服務端【傳送方】**:

import

socket

server=socket.socket()

server.bind((

"localhost

",1234))

server.listen()

while

true:

print("

正在等待。。。")

conn,addr=server.accept()

while

true:

try:

conn.send(b

"first info")

ack=conn.recv(1024) #

接收客戶端確認

print

(ack)

conn.send(b

"second info")

except

connectionreseterror as e:

print

(e)

break

server.close()

客戶端【接收方】**:

import

socket

client=socket.socket()

client.connect((

"localhost

",1234))

data=client.recv(1024)

print

(data.decode())

client.send(b

"ack

")#傳送確認

data=client.recv(1024)

print

(data.decode())

client.close()

由於資料太大,傳送方一次send不完,而接收方只recv一次,使得影響了後面資料的傳輸

解決根源的思想是改變recv的次數。

服務端【傳送方】:

import

socket,os

server=socket.socket()

server.bind((

"localhost

",1234))

server.listen()

while

true:

print("

正在等待...")

conn,addr=server.accept()

print("

連線成功!")

while

true:

try:

cmd=conn.recv(1024)

data=os.popen(cmd.decode()).read()

#print(data)

cmd_len=len(data.encode())

print

(cmd_len)

#發現這裡如果cmd_len為0會導致異常,有些是沒有返回值的command

if cmd_len==0:

data="

command has nothing return

"cmd_len=len(data.encode())

##因為這裡前面沒有傳送操作,所以不用擔心粘包,如果有則要考慮處理

conn.send(str(cmd_len).encode())#

因為len結果是int,所以還要轉換

#這裡要處理粘包

ack=conn.recv(1024)

conn.send(data.encode())

except

connectionreseterror as e:

print

(e)

break

server.close()

客戶端【接收方】:

import

socket

client=socket.socket()

client.connect((

"localhost

",1234))

while

true:

cmd = input("

>>:")

client.send(cmd.encode())

data_len=client.recv(1024)

data_len=int(data_len.decode())

print

(data_len)

recv_len=0

client.send(b

'ack')

total_data=b''

while recv_lendata=client.recv(1024)

recv_len+=len(data)

total_data+=data

print

(total_data.decode())

client.close()

socket中的粘包理解

粘包問題 傳送端傳送資料,接收端不知道應該如何接收而造成的一種資料混亂的現象 只有tcp協議才會傳送粘包 資料鏈路層 udp 傳輸層 不會發生 udp不會發生粘包,udp協議本層對一次收發資料大小的限制是 65535 ip包頭 20 udp包頭 8 65507針對 使用udp協議傳送資料,一次收發大...

Python中Socket粘包問題的解決

伺服器端 import socket import subprocess import struct server socket.socket ip port 192.168.15.33 8001 server.bind ip port server.listen conn,addr server....

Socket粘包問題的處理

當前在網路傳輸應用中,廣泛採用的是tcp ip通訊協議及其標準的socket應用開發程式設計介面 api tcp ip傳輸層有兩個並列的協議 tcp和udp。其中tcp transport control protocol,傳輸控制協議 是面向連線的,提供高可靠性服務。udp user datagr...