我們在傳輸數(shù)據(jù)時,經(jīng)常使用tcp/ip的服務(wù)器和客戶端模型,很多設(shè)備也經(jīng)常將網(wǎng)口作為硬件接口預(yù)留出來。可以使用 tcp/ip 傳輸圖像、大的文件等,如果圖片過大,還會進行拆分傳輸,接收方根據(jù)對應(yīng)協(xié)議進行解包。解包過程中可能會出現(xiàn) tcp 粘包現(xiàn)象,所以要根據(jù)對應(yīng)特性進行拆包。本次給大家分享一個小的 python 傳輸圖像的例子,由于數(shù)據(jù)量不大,沒有粘包的現(xiàn)象,以后會給大家分享一個 Qt 下使用 tcp/ip 根據(jù)對應(yīng)協(xié)議解析圖片的例子。
?
一般在發(fā)送圖片數(shù)據(jù)之前會先將圖片的大小等相關(guān)數(shù)據(jù)作為一包數(shù)據(jù)先發(fā)送,結(jié)束的時候會再次發(fā)送結(jié)束的數(shù)據(jù)包,根據(jù)包頭與包尾來判斷圖片接收組包是否完整。
?
運行環(huán)境:ubuntu 14.04
?
?
先來一個小流程圖:
CLIENT ??????????????????????????????????????SERVER
?????????????? ??? ?SIZE (image size)
?????????---------------------------------->
??????????????????????GOT SIZE ??
?????????<----------------------------------
?????????????????send image itself
?????????---------------------------------->
??????????????????????GOT IMAGE
?????????<----------------------------------
??????????????????????BYE BYE
?????????---------------------------------->
????????????????server closes socket
1.?Python client send image:
try:
# open image
myfile = open(image, 'rb')
bytes = myfile.read()
size = len(bytes)
# send image size to server
sock.sendall("SIZE %s" % size)
answer = sock.recv(4096)
print 'answer = %s' % answer
# send image to server
if answer == 'GOT SIZE':
sock.sendall(bytes)
# check what server send
answer = sock.recv(4096)
print 'answer = %s' % answer
if answer == 'GOT IMAGE' :
sock.sendall("BYE BYE ")
print 'Image successfully send to server'
myfile.close()
finally:
sock.close()
發(fā)送圖片是客戶端,主要是將圖片讀取為字節(jié),獲取字節(jié)大小,先發(fā)送到服務(wù)器端。之后等待服務(wù)器應(yīng)答,服務(wù)器向客戶端發(fā)送 'GOT SIZE' ,表明成功接收到圖片大小,之后客戶端發(fā)送圖片字節(jié)。這里面主要的就是如何讀取圖片為字節(jié)數(shù)據(jù)。
2.?Python server recv image:
while True:
read_sockets, write_sockets, error_sockets = select.select(connected_clients_sockets, [], [])
for sock in read_sockets:
if sock == server_socket:
sockfd, client_address = server_socket.accept()
connected_clients_sockets.append(sockfd)
else:
try:
data = sock.recv(4096)
txt = str(data)
if data:
if data.startswith('SIZE'):
tmp = txt.split()
size = int(tmp[1])
print 'got size'
sock.sendall("GOT SIZE")
elif data.startswith('BYE'):
sock.shutdown()
else :
myfile = open(basename % imgcounter, 'wb')
myfile.write(data)
data = sock.recv(40960000)
if not data:
myfile.close()
break
myfile.write(data)
myfile.close()
sock.sendall("GOT IMAGE")
sock.shutdown()
except:
sock.close()
connected_clients_sockets.remove(sock)
continue
imgcounter += 1
server_socket.close()
服務(wù)器這邊主要是接收到圖片字節(jié)數(shù)據(jù),將圖片寫到后綴為.png的文件中。
?
程序結(jié)果如下:
image3是接收到的圖片, dh 是被傳輸?shù)脑瓐D。 QtTcpServer 是用 Qt 寫的服務(wù)器接收圖片程序,下次再分享給大家。
如果需要完整程序,歡迎公眾號后臺留言,留下聯(lián)系方式。
本文主要供學(xué)習(xí)使用,不做商業(yè)用途,如果轉(zhuǎn)載請注明作者與出處,謝謝。
更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號聯(lián)系: 360901061
您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對您有幫助就好】元
