day32_python
2021/9/28 22:40:42
本文主要是介绍day32_python,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
参考Eva_J的博客,原文连接:https://www.cnblogs.com/Eva-J/p/7277026.html
主要知识
# 应用层协议ftp文件传输,http网页,smtp邮件相关的协议,https更加安全 ''' OSI模型 ''' # server ''' import socket sk = socket.socket() sk.bind(('127.0.0.1', 8000)) sk.listen() conn, addr = sk.accept() while 1: cmd = input('>>>') if cmd == 'q': conn.send(b'q') break conn.send(cmd.encode('gbk')) res = conn.recv(1024).decode('gbk') print(res) conn.close() sk.close() ''' # client端 ''' import subprocess import socket sk = socket.socket() sk.connect(('127.0.0.1', 8000)) sk.recv(1024).decode('gbk') while 1: cmd = sk.recv(1024).decode('gbk') if cmd == 'q': break res = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE) sk.send(res.stderr.read()) sk.send(res.stdout.read()) sk.close() ''' # 优化算法,连续的小数据包会被合并,已经被接收的就无法从缓存中读取了 # 多个send小数据连在一起,会发生黏包现象。 # tcp内部的优化算法是在短暂时间内会发生,加上一定时间的延时就好了,0.01s就可以 # 解决粘包问题的方式 # struct模块 ''' 该模块可以把一个类型,如数字,转成固定长度的bytes import struct ret = struct.pack('i', 4096) # 'i'即将要将一个数字专户为固定字节的bytes类型 print(ret) num = struct.unpack('i',ret) print(num[0]) 发送数据的时候,先发送长度,先接收一个长度 ''' # 管道中的数据只能取一次,类似于队列 ''' import queue q= queue.Queue() q.put(1) # 向队列中放数 print(q.qsize()) print(q.get()) # 取一次就pop print(q.qsize()) 在网络上传输的所有数据都叫做数据包,数据包里的所有的数据都叫报文 报文里面有ip、mac、端口号 报文根据协议有报头,都有报头 ''' # 定制报文 head = {'filename': 'demo', 'filesize': 409600, 'filetype': 'txt', 'filepath': r'\usr\bin'} # 报头的长度 先接收4个字节 # 根据4个字节获取报头 # 根据报头获取filesize,然后根据filesize接收文件 # 狭义上的协议网络协议是通信计算机双方必须共同遵从的一组约定。 ''' 如怎么样建立连接、怎么样互相识别等。 只有遵守这个约定,计算机之间才能相互通信交流。 协议往往分成几个层次进行定义,分层定义是为了使某一层协议的改变不影响其他层次的协议。 '''
文件的上传下载
server端
import socket import struct import json sk = socket.socket() sk.bind(('127.0.0.1', 8890)) sk.listen() buffer = 1024 conn, addr = sk.accept() head_len = conn.recv(4) # 报头长度 head_len = struct.unpack('i', head_len)[0] json_head = conn.recv(head_len).decode('utf-8') head = json.loads(json_head) filesize = head['filesize'] print('正在启动···') with open(head['filename'], 'wb')as f: while filesize: if filesize >= buffer: content = conn.recv(buffer) # 每次读出来的内容 f.write(content) filesize -= buffer else: content = conn.recv(filesize) f.write(content) break conn.close() sk.close()
client端
import socket import os import json import struct sk = socket.socket() buffer = 1024 sk.connect(('127.0.0.1', 8890)) head = {'filepath': r'F:\视频\internet', 'filename': r'千谎百计第一季-01.mp4', 'filesize': None} filepath = os.path.join(head['filepath'], head['filename']) filesize = os.path.getsize(filepath) head['filesize'] = filesize json_head = json.dumps(head) # 字典转成了字符串 byte_head = json_head.encode('utf-8') # 字符串转bytes head_len = len(byte_head) pack_len = struct.pack('i', head_len) sk.send(pack_len) # 先发报头的长度 sk.send(byte_head) # 再发送bytes类型的报头 print('正在启动···') with open(filepath, 'rb') as f: while filesize: if filesize >= buffer: content = f.read(buffer) # 每次读出来的内容 sk.send(content) filesize -= buffer else: content = f.read(filesize) sk.send(content) break print('已发完') sk.close()
这篇关于day32_python的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!
- 2024-12-27Python编程基础教程
- 2024-12-27Python编程基础指南
- 2024-12-24Python编程入门指南
- 2024-12-24Python编程基础入门
- 2024-12-24Python编程基础:变量与数据类型
- 2024-12-23使用python部署一个usdt合约,部署自己的usdt稳定币
- 2024-12-20Python编程入门指南
- 2024-12-20Python编程基础与进阶
- 2024-12-19Python基础编程教程
- 2024-12-19python 文件的后缀名是什么 怎么运行一个python文件?-icode9专业技术文章分享